diff --git a/spdy/core/array_output_buffer.cc b/spdy/core/array_output_buffer.cc
new file mode 100644
index 0000000..ea82eb0
--- /dev/null
+++ b/spdy/core/array_output_buffer.cc
@@ -0,0 +1,23 @@
+// Copyright 2017 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "net/third_party/quiche/src/spdy/core/array_output_buffer.h"
+
+namespace spdy {
+
+void ArrayOutputBuffer::Next(char** data, int* size) {
+  *data = current_;
+  *size = capacity_ > 0 ? capacity_ : 0;
+}
+
+void ArrayOutputBuffer::AdvanceWritePtr(int64_t count) {
+  current_ += count;
+  capacity_ -= count;
+}
+
+uint64_t ArrayOutputBuffer::BytesFree() const {
+  return capacity_;
+}
+
+}  // namespace spdy
diff --git a/spdy/core/array_output_buffer.h b/spdy/core/array_output_buffer.h
new file mode 100644
index 0000000..72303f1
--- /dev/null
+++ b/spdy/core/array_output_buffer.h
@@ -0,0 +1,45 @@
+// Copyright 2017 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef QUICHE_SPDY_CORE_ARRAY_OUTPUT_BUFFER_H_
+#define QUICHE_SPDY_CORE_ARRAY_OUTPUT_BUFFER_H_
+
+#include <cstddef>
+#include "net/third_party/quiche/src/spdy/core/zero_copy_output_buffer.h"
+
+namespace spdy {
+
+class ArrayOutputBuffer : public ZeroCopyOutputBuffer {
+ public:
+  // |buffer| is pointed to the output to write to, and |size| is the capacity
+  // of the output.
+  ArrayOutputBuffer(char* buffer, int64_t size)
+      : current_(buffer), begin_(buffer), capacity_(size) {}
+  ~ArrayOutputBuffer() override {}
+
+  ArrayOutputBuffer(const ArrayOutputBuffer&) = delete;
+  ArrayOutputBuffer& operator=(const ArrayOutputBuffer&) = delete;
+
+  void Next(char** data, int* size) override;
+  void AdvanceWritePtr(int64_t count) override;
+  uint64_t BytesFree() const override;
+
+  size_t Size() const { return current_ - begin_; }
+  char* Begin() const { return begin_; }
+
+  // Resets the buffer to its original state.
+  void Reset() {
+    capacity_ += Size();
+    current_ = begin_;
+  }
+
+ private:
+  char* current_ = nullptr;
+  char* begin_ = nullptr;
+  uint64_t capacity_ = 0;
+};
+
+}  // namespace spdy
+
+#endif  // QUICHE_SPDY_CORE_ARRAY_OUTPUT_BUFFER_H_
diff --git a/spdy/core/array_output_buffer_test.cc b/spdy/core/array_output_buffer_test.cc
new file mode 100644
index 0000000..369778d
--- /dev/null
+++ b/spdy/core/array_output_buffer_test.cc
@@ -0,0 +1,50 @@
+// Copyright 2017 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "net/third_party/quiche/src/spdy/core/array_output_buffer.h"
+
+#include "testing/gmock/include/gmock/gmock.h"
+#include "testing/gtest/include/gtest/gtest.h"
+
+namespace spdy {
+namespace test {
+
+// This test verifies that ArrayOutputBuffer is initialized properly.
+TEST(ArrayOutputBufferTest, InitializedFromArray) {
+  char array[100];
+  ArrayOutputBuffer buffer(array, sizeof(array));
+  EXPECT_EQ(sizeof(array), buffer.BytesFree());
+  EXPECT_EQ(0u, buffer.Size());
+  EXPECT_EQ(array, buffer.Begin());
+}
+
+// This test verifies that Reset() causes an ArrayOutputBuffer's capacity and
+// size to be reset to the initial state.
+TEST(ArrayOutputBufferTest, WriteAndReset) {
+  char array[100];
+  ArrayOutputBuffer buffer(array, sizeof(array));
+
+  // Let's write some bytes.
+  char* dst;
+  int size;
+  buffer.Next(&dst, &size);
+  ASSERT_GT(size, 1);
+  ASSERT_NE(nullptr, dst);
+  const int64_t written = size / 2;
+  memset(dst, 'x', written);
+  buffer.AdvanceWritePtr(written);
+
+  // The buffer should be partially used.
+  EXPECT_EQ(static_cast<uint64_t>(size) - written, buffer.BytesFree());
+  EXPECT_EQ(static_cast<uint64_t>(written), buffer.Size());
+
+  buffer.Reset();
+
+  // After a reset, the buffer should regain its full capacity.
+  EXPECT_EQ(sizeof(array), buffer.BytesFree());
+  EXPECT_EQ(0u, buffer.Size());
+}
+
+}  // namespace test
+}  // namespace spdy
diff --git a/spdy/core/hpack/hpack_constants.cc b/spdy/core/hpack/hpack_constants.cc
new file mode 100644
index 0000000..9c1498a
--- /dev/null
+++ b/spdy/core/hpack/hpack_constants.cc
@@ -0,0 +1,386 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_constants.h"
+
+#include <cstddef>
+#include <memory>
+#include <vector>
+
+#include "base/logging.h"
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_huffman_table.h"
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_static_table.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_arraysize.h"
+
+namespace spdy {
+
+// Produced by applying the python program [1] with tables provided by [2]
+// (inserted into the source of the python program) and copy-paste them into
+// this file.
+//
+// [1] net/tools/build_hpack_constants.py in Chromium
+// [2] http://tools.ietf.org/html/draft-ietf-httpbis-header-compression-08
+
+// HpackHuffmanSymbol entries are initialized as {code, length, id}.
+// Codes are specified in the |length| most-significant bits of |code|.
+const std::vector<HpackHuffmanSymbol>& HpackHuffmanCodeVector() {
+  static const auto* kHpackHuffmanCode = new std::vector<HpackHuffmanSymbol>{
+      {0xffc00000ul, 13, 0},    //     11111111|11000
+      {0xffffb000ul, 23, 1},    //     11111111|11111111|1011000
+      {0xfffffe20ul, 28, 2},    //     11111111|11111111|11111110|0010
+      {0xfffffe30ul, 28, 3},    //     11111111|11111111|11111110|0011
+      {0xfffffe40ul, 28, 4},    //     11111111|11111111|11111110|0100
+      {0xfffffe50ul, 28, 5},    //     11111111|11111111|11111110|0101
+      {0xfffffe60ul, 28, 6},    //     11111111|11111111|11111110|0110
+      {0xfffffe70ul, 28, 7},    //     11111111|11111111|11111110|0111
+      {0xfffffe80ul, 28, 8},    //     11111111|11111111|11111110|1000
+      {0xffffea00ul, 24, 9},    //     11111111|11111111|11101010
+      {0xfffffff0ul, 30, 10},   //     11111111|11111111|11111111|111100
+      {0xfffffe90ul, 28, 11},   //     11111111|11111111|11111110|1001
+      {0xfffffea0ul, 28, 12},   //     11111111|11111111|11111110|1010
+      {0xfffffff4ul, 30, 13},   //     11111111|11111111|11111111|111101
+      {0xfffffeb0ul, 28, 14},   //     11111111|11111111|11111110|1011
+      {0xfffffec0ul, 28, 15},   //     11111111|11111111|11111110|1100
+      {0xfffffed0ul, 28, 16},   //     11111111|11111111|11111110|1101
+      {0xfffffee0ul, 28, 17},   //     11111111|11111111|11111110|1110
+      {0xfffffef0ul, 28, 18},   //     11111111|11111111|11111110|1111
+      {0xffffff00ul, 28, 19},   //     11111111|11111111|11111111|0000
+      {0xffffff10ul, 28, 20},   //     11111111|11111111|11111111|0001
+      {0xffffff20ul, 28, 21},   //     11111111|11111111|11111111|0010
+      {0xfffffff8ul, 30, 22},   //     11111111|11111111|11111111|111110
+      {0xffffff30ul, 28, 23},   //     11111111|11111111|11111111|0011
+      {0xffffff40ul, 28, 24},   //     11111111|11111111|11111111|0100
+      {0xffffff50ul, 28, 25},   //     11111111|11111111|11111111|0101
+      {0xffffff60ul, 28, 26},   //     11111111|11111111|11111111|0110
+      {0xffffff70ul, 28, 27},   //     11111111|11111111|11111111|0111
+      {0xffffff80ul, 28, 28},   //     11111111|11111111|11111111|1000
+      {0xffffff90ul, 28, 29},   //     11111111|11111111|11111111|1001
+      {0xffffffa0ul, 28, 30},   //     11111111|11111111|11111111|1010
+      {0xffffffb0ul, 28, 31},   //     11111111|11111111|11111111|1011
+      {0x50000000ul, 6, 32},    // ' ' 010100
+      {0xfe000000ul, 10, 33},   // '!' 11111110|00
+      {0xfe400000ul, 10, 34},   // '"' 11111110|01
+      {0xffa00000ul, 12, 35},   // '#' 11111111|1010
+      {0xffc80000ul, 13, 36},   // '$' 11111111|11001
+      {0x54000000ul, 6, 37},    // '%' 010101
+      {0xf8000000ul, 8, 38},    // '&' 11111000
+      {0xff400000ul, 11, 39},   // ''' 11111111|010
+      {0xfe800000ul, 10, 40},   // '(' 11111110|10
+      {0xfec00000ul, 10, 41},   // ')' 11111110|11
+      {0xf9000000ul, 8, 42},    // '*' 11111001
+      {0xff600000ul, 11, 43},   // '+' 11111111|011
+      {0xfa000000ul, 8, 44},    // ',' 11111010
+      {0x58000000ul, 6, 45},    // '-' 010110
+      {0x5c000000ul, 6, 46},    // '.' 010111
+      {0x60000000ul, 6, 47},    // '/' 011000
+      {0x00000000ul, 5, 48},    // '0' 00000
+      {0x08000000ul, 5, 49},    // '1' 00001
+      {0x10000000ul, 5, 50},    // '2' 00010
+      {0x64000000ul, 6, 51},    // '3' 011001
+      {0x68000000ul, 6, 52},    // '4' 011010
+      {0x6c000000ul, 6, 53},    // '5' 011011
+      {0x70000000ul, 6, 54},    // '6' 011100
+      {0x74000000ul, 6, 55},    // '7' 011101
+      {0x78000000ul, 6, 56},    // '8' 011110
+      {0x7c000000ul, 6, 57},    // '9' 011111
+      {0xb8000000ul, 7, 58},    // ':' 1011100
+      {0xfb000000ul, 8, 59},    // ';' 11111011
+      {0xfff80000ul, 15, 60},   // '<' 11111111|1111100
+      {0x80000000ul, 6, 61},    // '=' 100000
+      {0xffb00000ul, 12, 62},   // '>' 11111111|1011
+      {0xff000000ul, 10, 63},   // '?' 11111111|00
+      {0xffd00000ul, 13, 64},   // '@' 11111111|11010
+      {0x84000000ul, 6, 65},    // 'A' 100001
+      {0xba000000ul, 7, 66},    // 'B' 1011101
+      {0xbc000000ul, 7, 67},    // 'C' 1011110
+      {0xbe000000ul, 7, 68},    // 'D' 1011111
+      {0xc0000000ul, 7, 69},    // 'E' 1100000
+      {0xc2000000ul, 7, 70},    // 'F' 1100001
+      {0xc4000000ul, 7, 71},    // 'G' 1100010
+      {0xc6000000ul, 7, 72},    // 'H' 1100011
+      {0xc8000000ul, 7, 73},    // 'I' 1100100
+      {0xca000000ul, 7, 74},    // 'J' 1100101
+      {0xcc000000ul, 7, 75},    // 'K' 1100110
+      {0xce000000ul, 7, 76},    // 'L' 1100111
+      {0xd0000000ul, 7, 77},    // 'M' 1101000
+      {0xd2000000ul, 7, 78},    // 'N' 1101001
+      {0xd4000000ul, 7, 79},    // 'O' 1101010
+      {0xd6000000ul, 7, 80},    // 'P' 1101011
+      {0xd8000000ul, 7, 81},    // 'Q' 1101100
+      {0xda000000ul, 7, 82},    // 'R' 1101101
+      {0xdc000000ul, 7, 83},    // 'S' 1101110
+      {0xde000000ul, 7, 84},    // 'T' 1101111
+      {0xe0000000ul, 7, 85},    // 'U' 1110000
+      {0xe2000000ul, 7, 86},    // 'V' 1110001
+      {0xe4000000ul, 7, 87},    // 'W' 1110010
+      {0xfc000000ul, 8, 88},    // 'X' 11111100
+      {0xe6000000ul, 7, 89},    // 'Y' 1110011
+      {0xfd000000ul, 8, 90},    // 'Z' 11111101
+      {0xffd80000ul, 13, 91},   // '[' 11111111|11011
+      {0xfffe0000ul, 19, 92},   // '\' 11111111|11111110|000
+      {0xffe00000ul, 13, 93},   // ']' 11111111|11100
+      {0xfff00000ul, 14, 94},   // '^' 11111111|111100
+      {0x88000000ul, 6, 95},    // '_' 100010
+      {0xfffa0000ul, 15, 96},   // '`' 11111111|1111101
+      {0x18000000ul, 5, 97},    // 'a' 00011
+      {0x8c000000ul, 6, 98},    // 'b' 100011
+      {0x20000000ul, 5, 99},    // 'c' 00100
+      {0x90000000ul, 6, 100},   // 'd' 100100
+      {0x28000000ul, 5, 101},   // 'e' 00101
+      {0x94000000ul, 6, 102},   // 'f' 100101
+      {0x98000000ul, 6, 103},   // 'g' 100110
+      {0x9c000000ul, 6, 104},   // 'h' 100111
+      {0x30000000ul, 5, 105},   // 'i' 00110
+      {0xe8000000ul, 7, 106},   // 'j' 1110100
+      {0xea000000ul, 7, 107},   // 'k' 1110101
+      {0xa0000000ul, 6, 108},   // 'l' 101000
+      {0xa4000000ul, 6, 109},   // 'm' 101001
+      {0xa8000000ul, 6, 110},   // 'n' 101010
+      {0x38000000ul, 5, 111},   // 'o' 00111
+      {0xac000000ul, 6, 112},   // 'p' 101011
+      {0xec000000ul, 7, 113},   // 'q' 1110110
+      {0xb0000000ul, 6, 114},   // 'r' 101100
+      {0x40000000ul, 5, 115},   // 's' 01000
+      {0x48000000ul, 5, 116},   // 't' 01001
+      {0xb4000000ul, 6, 117},   // 'u' 101101
+      {0xee000000ul, 7, 118},   // 'v' 1110111
+      {0xf0000000ul, 7, 119},   // 'w' 1111000
+      {0xf2000000ul, 7, 120},   // 'x' 1111001
+      {0xf4000000ul, 7, 121},   // 'y' 1111010
+      {0xf6000000ul, 7, 122},   // 'z' 1111011
+      {0xfffc0000ul, 15, 123},  // '{' 11111111|1111110
+      {0xff800000ul, 11, 124},  // '|' 11111111|100
+      {0xfff40000ul, 14, 125},  // '}' 11111111|111101
+      {0xffe80000ul, 13, 126},  // '~' 11111111|11101
+      {0xffffffc0ul, 28, 127},  //     11111111|11111111|11111111|1100
+      {0xfffe6000ul, 20, 128},  //     11111111|11111110|0110
+      {0xffff4800ul, 22, 129},  //     11111111|11111111|010010
+      {0xfffe7000ul, 20, 130},  //     11111111|11111110|0111
+      {0xfffe8000ul, 20, 131},  //     11111111|11111110|1000
+      {0xffff4c00ul, 22, 132},  //     11111111|11111111|010011
+      {0xffff5000ul, 22, 133},  //     11111111|11111111|010100
+      {0xffff5400ul, 22, 134},  //     11111111|11111111|010101
+      {0xffffb200ul, 23, 135},  //     11111111|11111111|1011001
+      {0xffff5800ul, 22, 136},  //     11111111|11111111|010110
+      {0xffffb400ul, 23, 137},  //     11111111|11111111|1011010
+      {0xffffb600ul, 23, 138},  //     11111111|11111111|1011011
+      {0xffffb800ul, 23, 139},  //     11111111|11111111|1011100
+      {0xffffba00ul, 23, 140},  //     11111111|11111111|1011101
+      {0xffffbc00ul, 23, 141},  //     11111111|11111111|1011110
+      {0xffffeb00ul, 24, 142},  //     11111111|11111111|11101011
+      {0xffffbe00ul, 23, 143},  //     11111111|11111111|1011111
+      {0xffffec00ul, 24, 144},  //     11111111|11111111|11101100
+      {0xffffed00ul, 24, 145},  //     11111111|11111111|11101101
+      {0xffff5c00ul, 22, 146},  //     11111111|11111111|010111
+      {0xffffc000ul, 23, 147},  //     11111111|11111111|1100000
+      {0xffffee00ul, 24, 148},  //     11111111|11111111|11101110
+      {0xffffc200ul, 23, 149},  //     11111111|11111111|1100001
+      {0xffffc400ul, 23, 150},  //     11111111|11111111|1100010
+      {0xffffc600ul, 23, 151},  //     11111111|11111111|1100011
+      {0xffffc800ul, 23, 152},  //     11111111|11111111|1100100
+      {0xfffee000ul, 21, 153},  //     11111111|11111110|11100
+      {0xffff6000ul, 22, 154},  //     11111111|11111111|011000
+      {0xffffca00ul, 23, 155},  //     11111111|11111111|1100101
+      {0xffff6400ul, 22, 156},  //     11111111|11111111|011001
+      {0xffffcc00ul, 23, 157},  //     11111111|11111111|1100110
+      {0xffffce00ul, 23, 158},  //     11111111|11111111|1100111
+      {0xffffef00ul, 24, 159},  //     11111111|11111111|11101111
+      {0xffff6800ul, 22, 160},  //     11111111|11111111|011010
+      {0xfffee800ul, 21, 161},  //     11111111|11111110|11101
+      {0xfffe9000ul, 20, 162},  //     11111111|11111110|1001
+      {0xffff6c00ul, 22, 163},  //     11111111|11111111|011011
+      {0xffff7000ul, 22, 164},  //     11111111|11111111|011100
+      {0xffffd000ul, 23, 165},  //     11111111|11111111|1101000
+      {0xffffd200ul, 23, 166},  //     11111111|11111111|1101001
+      {0xfffef000ul, 21, 167},  //     11111111|11111110|11110
+      {0xffffd400ul, 23, 168},  //     11111111|11111111|1101010
+      {0xffff7400ul, 22, 169},  //     11111111|11111111|011101
+      {0xffff7800ul, 22, 170},  //     11111111|11111111|011110
+      {0xfffff000ul, 24, 171},  //     11111111|11111111|11110000
+      {0xfffef800ul, 21, 172},  //     11111111|11111110|11111
+      {0xffff7c00ul, 22, 173},  //     11111111|11111111|011111
+      {0xffffd600ul, 23, 174},  //     11111111|11111111|1101011
+      {0xffffd800ul, 23, 175},  //     11111111|11111111|1101100
+      {0xffff0000ul, 21, 176},  //     11111111|11111111|00000
+      {0xffff0800ul, 21, 177},  //     11111111|11111111|00001
+      {0xffff8000ul, 22, 178},  //     11111111|11111111|100000
+      {0xffff1000ul, 21, 179},  //     11111111|11111111|00010
+      {0xffffda00ul, 23, 180},  //     11111111|11111111|1101101
+      {0xffff8400ul, 22, 181},  //     11111111|11111111|100001
+      {0xffffdc00ul, 23, 182},  //     11111111|11111111|1101110
+      {0xffffde00ul, 23, 183},  //     11111111|11111111|1101111
+      {0xfffea000ul, 20, 184},  //     11111111|11111110|1010
+      {0xffff8800ul, 22, 185},  //     11111111|11111111|100010
+      {0xffff8c00ul, 22, 186},  //     11111111|11111111|100011
+      {0xffff9000ul, 22, 187},  //     11111111|11111111|100100
+      {0xffffe000ul, 23, 188},  //     11111111|11111111|1110000
+      {0xffff9400ul, 22, 189},  //     11111111|11111111|100101
+      {0xffff9800ul, 22, 190},  //     11111111|11111111|100110
+      {0xffffe200ul, 23, 191},  //     11111111|11111111|1110001
+      {0xfffff800ul, 26, 192},  //     11111111|11111111|11111000|00
+      {0xfffff840ul, 26, 193},  //     11111111|11111111|11111000|01
+      {0xfffeb000ul, 20, 194},  //     11111111|11111110|1011
+      {0xfffe2000ul, 19, 195},  //     11111111|11111110|001
+      {0xffff9c00ul, 22, 196},  //     11111111|11111111|100111
+      {0xffffe400ul, 23, 197},  //     11111111|11111111|1110010
+      {0xffffa000ul, 22, 198},  //     11111111|11111111|101000
+      {0xfffff600ul, 25, 199},  //     11111111|11111111|11110110|0
+      {0xfffff880ul, 26, 200},  //     11111111|11111111|11111000|10
+      {0xfffff8c0ul, 26, 201},  //     11111111|11111111|11111000|11
+      {0xfffff900ul, 26, 202},  //     11111111|11111111|11111001|00
+      {0xfffffbc0ul, 27, 203},  //     11111111|11111111|11111011|110
+      {0xfffffbe0ul, 27, 204},  //     11111111|11111111|11111011|111
+      {0xfffff940ul, 26, 205},  //     11111111|11111111|11111001|01
+      {0xfffff100ul, 24, 206},  //     11111111|11111111|11110001
+      {0xfffff680ul, 25, 207},  //     11111111|11111111|11110110|1
+      {0xfffe4000ul, 19, 208},  //     11111111|11111110|010
+      {0xffff1800ul, 21, 209},  //     11111111|11111111|00011
+      {0xfffff980ul, 26, 210},  //     11111111|11111111|11111001|10
+      {0xfffffc00ul, 27, 211},  //     11111111|11111111|11111100|000
+      {0xfffffc20ul, 27, 212},  //     11111111|11111111|11111100|001
+      {0xfffff9c0ul, 26, 213},  //     11111111|11111111|11111001|11
+      {0xfffffc40ul, 27, 214},  //     11111111|11111111|11111100|010
+      {0xfffff200ul, 24, 215},  //     11111111|11111111|11110010
+      {0xffff2000ul, 21, 216},  //     11111111|11111111|00100
+      {0xffff2800ul, 21, 217},  //     11111111|11111111|00101
+      {0xfffffa00ul, 26, 218},  //     11111111|11111111|11111010|00
+      {0xfffffa40ul, 26, 219},  //     11111111|11111111|11111010|01
+      {0xffffffd0ul, 28, 220},  //     11111111|11111111|11111111|1101
+      {0xfffffc60ul, 27, 221},  //     11111111|11111111|11111100|011
+      {0xfffffc80ul, 27, 222},  //     11111111|11111111|11111100|100
+      {0xfffffca0ul, 27, 223},  //     11111111|11111111|11111100|101
+      {0xfffec000ul, 20, 224},  //     11111111|11111110|1100
+      {0xfffff300ul, 24, 225},  //     11111111|11111111|11110011
+      {0xfffed000ul, 20, 226},  //     11111111|11111110|1101
+      {0xffff3000ul, 21, 227},  //     11111111|11111111|00110
+      {0xffffa400ul, 22, 228},  //     11111111|11111111|101001
+      {0xffff3800ul, 21, 229},  //     11111111|11111111|00111
+      {0xffff4000ul, 21, 230},  //     11111111|11111111|01000
+      {0xffffe600ul, 23, 231},  //     11111111|11111111|1110011
+      {0xffffa800ul, 22, 232},  //     11111111|11111111|101010
+      {0xffffac00ul, 22, 233},  //     11111111|11111111|101011
+      {0xfffff700ul, 25, 234},  //     11111111|11111111|11110111|0
+      {0xfffff780ul, 25, 235},  //     11111111|11111111|11110111|1
+      {0xfffff400ul, 24, 236},  //     11111111|11111111|11110100
+      {0xfffff500ul, 24, 237},  //     11111111|11111111|11110101
+      {0xfffffa80ul, 26, 238},  //     11111111|11111111|11111010|10
+      {0xffffe800ul, 23, 239},  //     11111111|11111111|1110100
+      {0xfffffac0ul, 26, 240},  //     11111111|11111111|11111010|11
+      {0xfffffcc0ul, 27, 241},  //     11111111|11111111|11111100|110
+      {0xfffffb00ul, 26, 242},  //     11111111|11111111|11111011|00
+      {0xfffffb40ul, 26, 243},  //     11111111|11111111|11111011|01
+      {0xfffffce0ul, 27, 244},  //     11111111|11111111|11111100|111
+      {0xfffffd00ul, 27, 245},  //     11111111|11111111|11111101|000
+      {0xfffffd20ul, 27, 246},  //     11111111|11111111|11111101|001
+      {0xfffffd40ul, 27, 247},  //     11111111|11111111|11111101|010
+      {0xfffffd60ul, 27, 248},  //     11111111|11111111|11111101|011
+      {0xffffffe0ul, 28, 249},  //     11111111|11111111|11111111|1110
+      {0xfffffd80ul, 27, 250},  //     11111111|11111111|11111101|100
+      {0xfffffda0ul, 27, 251},  //     11111111|11111111|11111101|101
+      {0xfffffdc0ul, 27, 252},  //     11111111|11111111|11111101|110
+      {0xfffffde0ul, 27, 253},  //     11111111|11111111|11111101|111
+      {0xfffffe00ul, 27, 254},  //     11111111|11111111|11111110|000
+      {0xfffffb80ul, 26, 255},  //     11111111|11111111|11111011|10
+      {0xfffffffcul, 30, 256},  // EOS 11111111|11111111|11111111|111111
+  };
+  return *kHpackHuffmanCode;
+}
+
+// The "constructor" for a HpackStaticEntry that computes the lengths at
+// compile time.
+#define STATIC_ENTRY(name, value) \
+  { name, SPDY_ARRAYSIZE(name) - 1, value, SPDY_ARRAYSIZE(value) - 1 }
+
+const std::vector<HpackStaticEntry>& HpackStaticTableVector() {
+  static const auto* kHpackStaticTable = new std::vector<HpackStaticEntry>{
+      STATIC_ENTRY(":authority", ""),                    // 1
+      STATIC_ENTRY(":method", "GET"),                    // 2
+      STATIC_ENTRY(":method", "POST"),                   // 3
+      STATIC_ENTRY(":path", "/"),                        // 4
+      STATIC_ENTRY(":path", "/index.html"),              // 5
+      STATIC_ENTRY(":scheme", "http"),                   // 6
+      STATIC_ENTRY(":scheme", "https"),                  // 7
+      STATIC_ENTRY(":status", "200"),                    // 8
+      STATIC_ENTRY(":status", "204"),                    // 9
+      STATIC_ENTRY(":status", "206"),                    // 10
+      STATIC_ENTRY(":status", "304"),                    // 11
+      STATIC_ENTRY(":status", "400"),                    // 12
+      STATIC_ENTRY(":status", "404"),                    // 13
+      STATIC_ENTRY(":status", "500"),                    // 14
+      STATIC_ENTRY("accept-charset", ""),                // 15
+      STATIC_ENTRY("accept-encoding", "gzip, deflate"),  // 16
+      STATIC_ENTRY("accept-language", ""),               // 17
+      STATIC_ENTRY("accept-ranges", ""),                 // 18
+      STATIC_ENTRY("accept", ""),                        // 19
+      STATIC_ENTRY("access-control-allow-origin", ""),   // 20
+      STATIC_ENTRY("age", ""),                           // 21
+      STATIC_ENTRY("allow", ""),                         // 22
+      STATIC_ENTRY("authorization", ""),                 // 23
+      STATIC_ENTRY("cache-control", ""),                 // 24
+      STATIC_ENTRY("content-disposition", ""),           // 25
+      STATIC_ENTRY("content-encoding", ""),              // 26
+      STATIC_ENTRY("content-language", ""),              // 27
+      STATIC_ENTRY("content-length", ""),                // 28
+      STATIC_ENTRY("content-location", ""),              // 29
+      STATIC_ENTRY("content-range", ""),                 // 30
+      STATIC_ENTRY("content-type", ""),                  // 31
+      STATIC_ENTRY("cookie", ""),                        // 32
+      STATIC_ENTRY("date", ""),                          // 33
+      STATIC_ENTRY("etag", ""),                          // 34
+      STATIC_ENTRY("expect", ""),                        // 35
+      STATIC_ENTRY("expires", ""),                       // 36
+      STATIC_ENTRY("from", ""),                          // 37
+      STATIC_ENTRY("host", ""),                          // 38
+      STATIC_ENTRY("if-match", ""),                      // 39
+      STATIC_ENTRY("if-modified-since", ""),             // 40
+      STATIC_ENTRY("if-none-match", ""),                 // 41
+      STATIC_ENTRY("if-range", ""),                      // 42
+      STATIC_ENTRY("if-unmodified-since", ""),           // 43
+      STATIC_ENTRY("last-modified", ""),                 // 44
+      STATIC_ENTRY("link", ""),                          // 45
+      STATIC_ENTRY("location", ""),                      // 46
+      STATIC_ENTRY("max-forwards", ""),                  // 47
+      STATIC_ENTRY("proxy-authenticate", ""),            // 48
+      STATIC_ENTRY("proxy-authorization", ""),           // 49
+      STATIC_ENTRY("range", ""),                         // 50
+      STATIC_ENTRY("referer", ""),                       // 51
+      STATIC_ENTRY("refresh", ""),                       // 52
+      STATIC_ENTRY("retry-after", ""),                   // 53
+      STATIC_ENTRY("server", ""),                        // 54
+      STATIC_ENTRY("set-cookie", ""),                    // 55
+      STATIC_ENTRY("strict-transport-security", ""),     // 56
+      STATIC_ENTRY("transfer-encoding", ""),             // 57
+      STATIC_ENTRY("user-agent", ""),                    // 58
+      STATIC_ENTRY("vary", ""),                          // 59
+      STATIC_ENTRY("via", ""),                           // 60
+      STATIC_ENTRY("www-authenticate", ""),              // 61
+  };
+  return *kHpackStaticTable;
+}
+
+#undef STATIC_ENTRY
+
+const HpackHuffmanTable& ObtainHpackHuffmanTable() {
+  static const HpackHuffmanTable* const shared_huffman_table = []() {
+    auto* table = new HpackHuffmanTable();
+    CHECK(table->Initialize(HpackHuffmanCodeVector().data(),
+                            HpackHuffmanCodeVector().size()));
+    CHECK(table->IsInitialized());
+    return table;
+  }();
+  return *shared_huffman_table;
+}
+
+const HpackStaticTable& ObtainHpackStaticTable() {
+  static const HpackStaticTable* const shared_static_table = []() {
+    auto* table = new HpackStaticTable();
+    table->Initialize(HpackStaticTableVector().data(),
+                      HpackStaticTableVector().size());
+    CHECK(table->IsInitialized());
+    return table;
+  }();
+  return *shared_static_table;
+}
+
+}  // namespace spdy
diff --git a/spdy/core/hpack/hpack_constants.h b/spdy/core/hpack/hpack_constants.h
new file mode 100644
index 0000000..3f4026b
--- /dev/null
+++ b/spdy/core/hpack/hpack_constants.h
@@ -0,0 +1,95 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef QUICHE_SPDY_CORE_HPACK_HPACK_CONSTANTS_H_
+#define QUICHE_SPDY_CORE_HPACK_HPACK_CONSTANTS_H_
+
+#include <cstddef>
+#include <cstdint>
+#include <vector>
+
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_export.h"
+
+// All section references below are to
+// http://tools.ietf.org/html/draft-ietf-httpbis-header-compression-08
+
+namespace spdy {
+
+// An HpackPrefix signifies |bits| stored in the top |bit_size| bits
+// of an octet.
+struct HpackPrefix {
+  uint8_t bits;
+  size_t bit_size;
+};
+
+// Represents a symbol and its Huffman code (stored in most-significant bits).
+struct HpackHuffmanSymbol {
+  uint32_t code;
+  uint8_t length;
+  uint16_t id;
+};
+
+// An entry in the static table. Must be a POD in order to avoid static
+// initializers, i.e. no user-defined constructors or destructors.
+struct HpackStaticEntry {
+  const char* const name;
+  const size_t name_len;
+  const char* const value;
+  const size_t value_len;
+};
+
+class HpackHuffmanTable;
+class HpackStaticTable;
+
+// Defined in RFC 7540, 6.5.2.
+const uint32_t kDefaultHeaderTableSizeSetting = 4096;
+
+// RFC 7541, 5.2: Flag for a string literal that is stored unmodified (i.e.,
+// without Huffman encoding).
+const HpackPrefix kStringLiteralIdentityEncoded = {0x0, 1};
+
+// RFC 7541, 5.2: Flag for a Huffman-coded string literal.
+const HpackPrefix kStringLiteralHuffmanEncoded = {0x1, 1};
+
+// RFC 7541, 6.1: Opcode for an indexed header field.
+const HpackPrefix kIndexedOpcode = {0b1, 1};
+
+// RFC 7541, 6.2.1: Opcode for a literal header field with incremental indexing.
+const HpackPrefix kLiteralIncrementalIndexOpcode = {0b01, 2};
+
+// RFC 7541, 6.2.2: Opcode for a literal header field without indexing.
+const HpackPrefix kLiteralNoIndexOpcode = {0b0000, 4};
+
+// RFC 7541, 6.2.3: Opcode for a literal header field which is never indexed.
+// Currently unused.
+// const HpackPrefix kLiteralNeverIndexOpcode = {0b0001, 4};
+
+// RFC 7541, 6.3: Opcode for maximum header table size update. Begins a
+// varint-encoded table size with a 5-bit prefix.
+const HpackPrefix kHeaderTableSizeUpdateOpcode = {0b001, 3};
+
+// Symbol code table from RFC 7541, "Appendix C. Huffman Code".
+SPDY_EXPORT_PRIVATE const std::vector<HpackHuffmanSymbol>&
+HpackHuffmanCodeVector();
+
+// Static table from RFC 7541, "Appendix B. Static Table Definition".
+SPDY_EXPORT_PRIVATE const std::vector<HpackStaticEntry>&
+HpackStaticTableVector();
+
+// Returns a HpackHuffmanTable instance initialized with |kHpackHuffmanCode|.
+// The instance is read-only, has static lifetime, and is safe to share amoung
+// threads. This function is thread-safe.
+SPDY_EXPORT_PRIVATE const HpackHuffmanTable& ObtainHpackHuffmanTable();
+
+// Returns a HpackStaticTable instance initialized with |kHpackStaticTable|.
+// The instance is read-only, has static lifetime, and is safe to share amoung
+// threads. This function is thread-safe.
+SPDY_EXPORT_PRIVATE const HpackStaticTable& ObtainHpackStaticTable();
+
+// Pseudo-headers start with a colon.  (HTTP2 8.1.2.1., HPACK 3.1.)
+const char kPseudoHeaderPrefix = ':';
+
+}  // namespace spdy
+
+#endif  // QUICHE_SPDY_CORE_HPACK_HPACK_CONSTANTS_H_
diff --git a/spdy/core/hpack/hpack_decoder_adapter.cc b/spdy/core/hpack/hpack_decoder_adapter.cc
new file mode 100644
index 0000000..309af39
--- /dev/null
+++ b/spdy/core/hpack/hpack_decoder_adapter.cc
@@ -0,0 +1,201 @@
+// Copyright 2017 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_decoder_adapter.h"
+
+#include "base/logging.h"
+#include "net/third_party/quiche/src/http2/decoder/decode_buffer.h"
+#include "net/third_party/quiche/src/http2/decoder/decode_status.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_estimate_memory_usage.h"
+
+using ::http2::DecodeBuffer;
+using ::http2::HpackEntryType;
+using ::http2::HpackString;
+
+namespace spdy {
+namespace {
+const size_t kMaxDecodeBufferSizeBytes = 32 * 1024;  // 32 KB
+}  // namespace
+
+HpackDecoderAdapter::HpackDecoderAdapter()
+    : hpack_decoder_(&listener_adapter_, kMaxDecodeBufferSizeBytes),
+      max_decode_buffer_size_bytes_(kMaxDecodeBufferSizeBytes),
+      header_block_started_(false) {}
+
+HpackDecoderAdapter::~HpackDecoderAdapter() = default;
+
+void HpackDecoderAdapter::ApplyHeaderTableSizeSetting(size_t size_setting) {
+  DVLOG(2) << "HpackDecoderAdapter::ApplyHeaderTableSizeSetting";
+  hpack_decoder_.ApplyHeaderTableSizeSetting(size_setting);
+}
+
+void HpackDecoderAdapter::HandleControlFrameHeadersStart(
+    SpdyHeadersHandlerInterface* handler) {
+  DVLOG(2) << "HpackDecoderAdapter::HandleControlFrameHeadersStart";
+  DCHECK(!header_block_started_);
+  listener_adapter_.set_handler(handler);
+}
+
+bool HpackDecoderAdapter::HandleControlFrameHeadersData(
+    const char* headers_data,
+    size_t headers_data_length) {
+  DVLOG(2) << "HpackDecoderAdapter::HandleControlFrameHeadersData: len="
+           << headers_data_length;
+  if (!header_block_started_) {
+    // Initialize the decoding process here rather than in
+    // HandleControlFrameHeadersStart because that method is not always called.
+    header_block_started_ = true;
+    if (!hpack_decoder_.StartDecodingBlock()) {
+      header_block_started_ = false;
+      return false;
+    }
+  }
+
+  // Sometimes we get a call with headers_data==nullptr and
+  // headers_data_length==0, in which case we need to avoid creating
+  // a DecodeBuffer, which would otherwise complain.
+  if (headers_data_length > 0) {
+    DCHECK_NE(headers_data, nullptr);
+    if (headers_data_length > max_decode_buffer_size_bytes_) {
+      DVLOG(1) << "max_decode_buffer_size_bytes_ < headers_data_length: "
+               << max_decode_buffer_size_bytes_ << " < " << headers_data_length;
+      return false;
+    }
+    listener_adapter_.AddToTotalHpackBytes(headers_data_length);
+    http2::DecodeBuffer db(headers_data, headers_data_length);
+    bool ok = hpack_decoder_.DecodeFragment(&db);
+    DCHECK(!ok || db.Empty()) << "Remaining=" << db.Remaining();
+    return ok;
+  }
+  return true;
+}
+
+bool HpackDecoderAdapter::HandleControlFrameHeadersComplete(
+    size_t* compressed_len) {
+  DVLOG(2) << "HpackDecoderAdapter::HandleControlFrameHeadersComplete";
+  if (compressed_len != nullptr) {
+    *compressed_len = listener_adapter_.total_hpack_bytes();
+  }
+  if (!hpack_decoder_.EndDecodingBlock()) {
+    DVLOG(3) << "EndDecodingBlock returned false";
+    return false;
+  }
+  header_block_started_ = false;
+  return true;
+}
+
+const SpdyHeaderBlock& HpackDecoderAdapter::decoded_block() const {
+  return listener_adapter_.decoded_block();
+}
+
+void HpackDecoderAdapter::SetHeaderTableDebugVisitor(
+    std::unique_ptr<HpackHeaderTable::DebugVisitorInterface> visitor) {
+  DVLOG(2) << "HpackDecoderAdapter::SetHeaderTableDebugVisitor";
+  if (visitor != nullptr) {
+    listener_adapter_.SetHeaderTableDebugVisitor(std::move(visitor));
+    hpack_decoder_.set_tables_debug_listener(&listener_adapter_);
+  } else {
+    hpack_decoder_.set_tables_debug_listener(nullptr);
+    listener_adapter_.SetHeaderTableDebugVisitor(nullptr);
+  }
+}
+
+void HpackDecoderAdapter::set_max_decode_buffer_size_bytes(
+    size_t max_decode_buffer_size_bytes) {
+  DVLOG(2) << "HpackDecoderAdapter::set_max_decode_buffer_size_bytes";
+  max_decode_buffer_size_bytes_ = max_decode_buffer_size_bytes;
+  hpack_decoder_.set_max_string_size_bytes(max_decode_buffer_size_bytes);
+}
+
+size_t HpackDecoderAdapter::EstimateMemoryUsage() const {
+  return SpdyEstimateMemoryUsage(hpack_decoder_);
+}
+
+HpackDecoderAdapter::ListenerAdapter::ListenerAdapter() : handler_(nullptr) {}
+HpackDecoderAdapter::ListenerAdapter::~ListenerAdapter() = default;
+
+void HpackDecoderAdapter::ListenerAdapter::set_handler(
+    SpdyHeadersHandlerInterface* handler) {
+  handler_ = handler;
+}
+
+void HpackDecoderAdapter::ListenerAdapter::SetHeaderTableDebugVisitor(
+    std::unique_ptr<HpackHeaderTable::DebugVisitorInterface> visitor) {
+  visitor_ = std::move(visitor);
+}
+
+void HpackDecoderAdapter::ListenerAdapter::OnHeaderListStart() {
+  DVLOG(2) << "HpackDecoderAdapter::ListenerAdapter::OnHeaderListStart";
+  total_hpack_bytes_ = 0;
+  total_uncompressed_bytes_ = 0;
+  decoded_block_.clear();
+  if (handler_ != nullptr) {
+    handler_->OnHeaderBlockStart();
+  }
+}
+
+void HpackDecoderAdapter::ListenerAdapter::OnHeader(HpackEntryType entry_type,
+                                                    const HpackString& name,
+                                                    const HpackString& value) {
+  DVLOG(2) << "HpackDecoderAdapter::ListenerAdapter::OnHeader:\n name: " << name
+           << "\n value: " << value;
+  total_uncompressed_bytes_ += name.size() + value.size();
+  if (handler_ == nullptr) {
+    DVLOG(3) << "Adding to decoded_block";
+    decoded_block_.AppendValueOrAddHeader(name.ToStringPiece(),
+                                          value.ToStringPiece());
+  } else {
+    DVLOG(3) << "Passing to handler";
+    handler_->OnHeader(name.ToStringPiece(), value.ToStringPiece());
+  }
+}
+
+void HpackDecoderAdapter::ListenerAdapter::OnHeaderListEnd() {
+  DVLOG(2) << "HpackDecoderAdapter::ListenerAdapter::OnHeaderListEnd";
+  // We don't clear the SpdyHeaderBlock here to allow access to it until the
+  // next HPACK block is decoded.
+  if (handler_ != nullptr) {
+    handler_->OnHeaderBlockEnd(total_uncompressed_bytes_, total_hpack_bytes_);
+    handler_ = nullptr;
+  }
+}
+
+void HpackDecoderAdapter::ListenerAdapter::OnHeaderErrorDetected(
+    SpdyStringPiece error_message) {
+  VLOG(1) << error_message;
+}
+
+int64_t HpackDecoderAdapter::ListenerAdapter::OnEntryInserted(
+    const http2::HpackStringPair& sp,
+    size_t insert_count) {
+  DVLOG(2) << "HpackDecoderAdapter::ListenerAdapter::OnEntryInserted: " << sp
+           << ",  insert_count=" << insert_count;
+  if (visitor_ == nullptr) {
+    return 0;
+  }
+  HpackEntry entry(sp.name.ToStringPiece(), sp.value.ToStringPiece(),
+                   /*is_static*/ false, insert_count);
+  int64_t time_added = visitor_->OnNewEntry(entry);
+  DVLOG(2)
+      << "HpackDecoderAdapter::ListenerAdapter::OnEntryInserted: time_added="
+      << time_added;
+  return time_added;
+}
+
+void HpackDecoderAdapter::ListenerAdapter::OnUseEntry(
+    const http2::HpackStringPair& sp,
+    size_t insert_count,
+    int64_t time_added) {
+  DVLOG(2) << "HpackDecoderAdapter::ListenerAdapter::OnUseEntry: " << sp
+           << ",  insert_count=" << insert_count
+           << ",  time_added=" << time_added;
+  if (visitor_ != nullptr) {
+    HpackEntry entry(sp.name.ToStringPiece(), sp.value.ToStringPiece(),
+                     /*is_static*/ false, insert_count);
+    entry.set_time_added(time_added);
+    visitor_->OnUseEntry(entry);
+  }
+}
+
+}  // namespace spdy
diff --git a/spdy/core/hpack/hpack_decoder_adapter.h b/spdy/core/hpack/hpack_decoder_adapter.h
new file mode 100644
index 0000000..b497fe7
--- /dev/null
+++ b/spdy/core/hpack/hpack_decoder_adapter.h
@@ -0,0 +1,159 @@
+// Copyright 2017 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef QUICHE_SPDY_CORE_HPACK_HPACK_DECODER_ADAPTER_H_
+#define QUICHE_SPDY_CORE_HPACK_HPACK_DECODER_ADAPTER_H_
+
+// HpackDecoderAdapter uses http2::HpackDecoder to decode HPACK blocks into
+// HTTP/2 header lists as outlined in http://tools.ietf.org/html/rfc7541.
+
+#include <stddef.h>
+
+#include <cstdint>
+#include <memory>
+
+#include "base/macros.h"
+#include "net/third_party/quiche/src/http2/hpack/decoder/hpack_decoder.h"
+#include "net/third_party/quiche/src/http2/hpack/decoder/hpack_decoder_listener.h"
+#include "net/third_party/quiche/src/http2/hpack/decoder/hpack_decoder_tables.h"
+#include "net/third_party/quiche/src/http2/hpack/hpack_string.h"
+#include "net/third_party/quiche/src/http2/hpack/http2_hpack_constants.h"
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_header_table.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_header_block.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_headers_handler_interface.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_export.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string_piece.h"
+
+namespace spdy {
+namespace test {
+class HpackDecoderAdapterPeer;
+}  // namespace test
+
+class SPDY_EXPORT_PRIVATE HpackDecoderAdapter {
+ public:
+  friend test::HpackDecoderAdapterPeer;
+  HpackDecoderAdapter();
+  HpackDecoderAdapter(const HpackDecoderAdapter&) = delete;
+  HpackDecoderAdapter& operator=(const HpackDecoderAdapter&) = delete;
+  ~HpackDecoderAdapter();
+
+  // Called upon acknowledgement of SETTINGS_HEADER_TABLE_SIZE.
+  void ApplyHeaderTableSizeSetting(size_t size_setting);
+
+  // If a SpdyHeadersHandlerInterface is provided, the decoder will emit
+  // headers to it rather than accumulating them in a SpdyHeaderBlock.
+  // Does not take ownership of the handler, but does use the pointer until
+  // the current HPACK block is completely decoded.
+  void HandleControlFrameHeadersStart(SpdyHeadersHandlerInterface* handler);
+
+  // Called as HPACK block fragments arrive. Returns false if an error occurred
+  // while decoding the block. Does not take ownership of headers_data.
+  bool HandleControlFrameHeadersData(const char* headers_data,
+                                     size_t headers_data_length);
+
+  // Called after a HPACK block has been completely delivered via
+  // HandleControlFrameHeadersData(). Returns false if an error occurred.
+  // |compressed_len| if non-null will be set to the size of the encoded
+  // buffered block that was accumulated in HandleControlFrameHeadersData(),
+  // to support subsequent calculation of compression percentage.
+  // Discards the handler supplied at the start of decoding the block.
+  // TODO(jamessynge): Determine if compressed_len is needed; it is used to
+  // produce UUMA stat Net.SpdyHpackDecompressionPercentage, but only for
+  // deprecated SPDY3.
+  bool HandleControlFrameHeadersComplete(size_t* compressed_len);
+
+  // Accessor for the most recently decoded headers block. Valid until the next
+  // call to HandleControlFrameHeadersData().
+  // TODO(birenroy): Remove this method when all users of HpackDecoder specify
+  // a SpdyHeadersHandlerInterface.
+  const SpdyHeaderBlock& decoded_block() const;
+
+  void SetHeaderTableDebugVisitor(
+      std::unique_ptr<HpackHeaderTable::DebugVisitorInterface> visitor);
+
+  // Set how much encoded data this decoder is willing to buffer.
+  // TODO(jamessynge): Resolve definition of this value, as it is currently
+  // too tied to a single implementation. We probably want to limit one or more
+  // of these: individual name or value strings, header entries, the entire
+  // header list, or the HPACK block; we probably shouldn't care about the size
+  // of individual transport buffers.
+  void set_max_decode_buffer_size_bytes(size_t max_decode_buffer_size_bytes);
+
+  size_t EstimateMemoryUsage() const;
+
+ private:
+  class SPDY_EXPORT_PRIVATE ListenerAdapter
+      : public http2::HpackDecoderListener,
+        public http2::HpackDecoderTablesDebugListener {
+   public:
+    ListenerAdapter();
+    ~ListenerAdapter() override;
+
+    // If a SpdyHeadersHandlerInterface is provided, the decoder will emit
+    // headers to it rather than accumulating them in a SpdyHeaderBlock.
+    // Does not take ownership of the handler, but does use the pointer until
+    // the current HPACK block is completely decoded.
+    void set_handler(SpdyHeadersHandlerInterface* handler);
+    const SpdyHeaderBlock& decoded_block() const { return decoded_block_; }
+
+    void SetHeaderTableDebugVisitor(
+        std::unique_ptr<HpackHeaderTable::DebugVisitorInterface> visitor);
+
+    // Override the HpackDecoderListener methods:
+    void OnHeaderListStart() override;
+    void OnHeader(http2::HpackEntryType entry_type,
+                  const http2::HpackString& name,
+                  const http2::HpackString& value) override;
+    void OnHeaderListEnd() override;
+    void OnHeaderErrorDetected(SpdyStringPiece error_message) override;
+
+    // Override the HpackDecoderTablesDebugListener methods:
+    int64_t OnEntryInserted(const http2::HpackStringPair& entry,
+                            size_t insert_count) override;
+    void OnUseEntry(const http2::HpackStringPair& entry,
+                    size_t insert_count,
+                    int64_t insert_time) override;
+
+    void AddToTotalHpackBytes(size_t delta) { total_hpack_bytes_ += delta; }
+    size_t total_hpack_bytes() const { return total_hpack_bytes_; }
+
+   private:
+    // If the caller doesn't provide a handler, the header list is stored in
+    // this SpdyHeaderBlock.
+    SpdyHeaderBlock decoded_block_;
+
+    // If non-NULL, handles decoded headers. Not owned.
+    SpdyHeadersHandlerInterface* handler_;
+
+    // Total bytes that have been received as input (i.e. HPACK encoded)
+    // in the current HPACK block.
+    size_t total_hpack_bytes_;
+
+    // Total bytes of the name and value strings in the current HPACK block.
+    size_t total_uncompressed_bytes_;
+
+    // visitor_ is used by a QUIC experiment regarding HPACK; remove
+    // when the experiment is done.
+    std::unique_ptr<HpackHeaderTable::DebugVisitorInterface> visitor_;
+  };
+
+  // Converts calls to HpackDecoderListener into calls to
+  // SpdyHeadersHandlerInterface.
+  ListenerAdapter listener_adapter_;
+
+  // The actual decoder.
+  http2::HpackDecoder hpack_decoder_;
+
+  // How much encoded data this decoder is willing to buffer.
+  size_t max_decode_buffer_size_bytes_;
+
+  // Flag to keep track of having seen the header block start. Needed at the
+  // moment because HandleControlFrameHeadersStart won't be called if a handler
+  // is not being provided by the caller.
+  bool header_block_started_;
+};
+
+}  // namespace spdy
+
+#endif  // QUICHE_SPDY_CORE_HPACK_HPACK_DECODER_ADAPTER_H_
diff --git a/spdy/core/hpack/hpack_decoder_adapter_test.cc b/spdy/core/hpack/hpack_decoder_adapter_test.cc
new file mode 100644
index 0000000..765c2ea
--- /dev/null
+++ b/spdy/core/hpack/hpack_decoder_adapter_test.cc
@@ -0,0 +1,1097 @@
+// Copyright 2017 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_decoder_adapter.h"
+
+// Tests of HpackDecoderAdapter.
+
+#include <stdint.h>
+
+#include <tuple>
+#include <utility>
+#include <vector>
+
+#include "base/logging.h"
+#include "testing/gmock/include/gmock/gmock.h"
+#include "testing/gtest/include/gtest/gtest.h"
+#include "net/third_party/quiche/src/http2/hpack/decoder/hpack_decoder_state.h"
+#include "net/third_party/quiche/src/http2/hpack/decoder/hpack_decoder_tables.h"
+#include "net/third_party/quiche/src/http2/hpack/tools/hpack_block_builder.h"
+#include "net/third_party/quiche/src/http2/test_tools/http2_random.h"
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_constants.h"
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_encoder.h"
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_output_stream.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_test_utils.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_arraysize.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string_utils.h"
+
+using ::http2::HpackEntryType;
+using ::http2::HpackString;
+using ::http2::HpackStringPair;
+using ::http2::test::HpackBlockBuilder;
+using ::http2::test::HpackDecoderPeer;
+using ::testing::ElementsAre;
+using ::testing::Pair;
+
+namespace http2 {
+namespace test {
+
+class HpackDecoderStatePeer {
+ public:
+  static HpackDecoderTables* GetDecoderTables(HpackDecoderState* state) {
+    return &state->decoder_tables_;
+  }
+};
+
+class HpackDecoderPeer {
+ public:
+  static HpackDecoderState* GetDecoderState(HpackDecoder* decoder) {
+    return &decoder->decoder_state_;
+  }
+  static HpackDecoderTables* GetDecoderTables(HpackDecoder* decoder) {
+    return HpackDecoderStatePeer::GetDecoderTables(GetDecoderState(decoder));
+  }
+};
+
+}  // namespace test
+}  // namespace http2
+
+namespace spdy {
+namespace test {
+
+class HpackDecoderAdapterPeer {
+ public:
+  explicit HpackDecoderAdapterPeer(HpackDecoderAdapter* decoder)
+      : decoder_(decoder) {}
+
+  void HandleHeaderRepresentation(SpdyStringPiece name, SpdyStringPiece value) {
+    decoder_->listener_adapter_.OnHeader(HpackEntryType::kIndexedLiteralHeader,
+                                         HpackString(name), HpackString(value));
+  }
+
+  http2::HpackDecoderTables* GetDecoderTables() {
+    return HpackDecoderPeer::GetDecoderTables(&decoder_->hpack_decoder_);
+  }
+
+  const HpackStringPair* GetTableEntry(uint32_t index) {
+    return GetDecoderTables()->Lookup(index);
+  }
+
+  size_t current_header_table_size() {
+    return GetDecoderTables()->current_header_table_size();
+  }
+
+  size_t header_table_size_limit() {
+    return GetDecoderTables()->header_table_size_limit();
+  }
+
+  void set_header_table_size_limit(size_t size) {
+    return GetDecoderTables()->DynamicTableSizeUpdate(size);
+  }
+
+ private:
+  HpackDecoderAdapter* decoder_;
+};
+
+class HpackEncoderPeer {
+ public:
+  static void CookieToCrumbs(const HpackEncoder::Representation& cookie,
+                             HpackEncoder::Representations* crumbs_out) {
+    HpackEncoder::CookieToCrumbs(cookie, crumbs_out);
+  }
+};
+
+namespace {
+
+const bool kNoCheckDecodedSize = false;
+const char* kCookieKey = "cookie";
+
+// Is HandleControlFrameHeadersStart to be called, and with what value?
+enum StartChoice { START_WITH_HANDLER, START_WITHOUT_HANDLER, NO_START };
+
+class HpackDecoderAdapterTest
+    : public ::testing::TestWithParam<std::tuple<StartChoice, bool>> {
+ protected:
+  HpackDecoderAdapterTest() : decoder_(), decoder_peer_(&decoder_) {}
+
+  void SetUp() override {
+    std::tie(start_choice_, randomly_split_input_buffer_) = GetParam();
+  }
+
+  void HandleControlFrameHeadersStart() {
+    bytes_passed_in_ = 0;
+    switch (start_choice_) {
+      case START_WITH_HANDLER:
+        decoder_.HandleControlFrameHeadersStart(&handler_);
+        break;
+      case START_WITHOUT_HANDLER:
+        decoder_.HandleControlFrameHeadersStart(nullptr);
+        break;
+      case NO_START:
+        break;
+    }
+  }
+
+  bool HandleControlFrameHeadersData(SpdyStringPiece str) {
+    VLOG(3) << "HandleControlFrameHeadersData:\n" << SpdyHexDump(str);
+    bytes_passed_in_ += str.size();
+    return decoder_.HandleControlFrameHeadersData(str.data(), str.size());
+  }
+
+  bool HandleControlFrameHeadersComplete(size_t* size) {
+    bool rc = decoder_.HandleControlFrameHeadersComplete(size);
+    if (size != nullptr) {
+      EXPECT_EQ(*size, bytes_passed_in_);
+    }
+    return rc;
+  }
+
+  bool DecodeHeaderBlock(SpdyStringPiece str, bool check_decoded_size = true) {
+    // Don't call this again if HandleControlFrameHeadersData failed previously.
+    EXPECT_FALSE(decode_has_failed_);
+    HandleControlFrameHeadersStart();
+    if (randomly_split_input_buffer_) {
+      do {
+        // Decode some fragment of the remaining bytes.
+        size_t bytes = str.size();
+        if (!str.empty()) {
+          bytes = random_.Uniform(str.size()) + 1;
+        }
+        EXPECT_LE(bytes, str.size());
+        if (!HandleControlFrameHeadersData(str.substr(0, bytes))) {
+          decode_has_failed_ = true;
+          return false;
+        }
+        str.remove_prefix(bytes);
+      } while (!str.empty());
+    } else if (!HandleControlFrameHeadersData(str)) {
+      decode_has_failed_ = true;
+      return false;
+    }
+    // Want to get out the number of compressed bytes that were decoded,
+    // so pass in a pointer if no handler.
+    size_t total_hpack_bytes = 0;
+    if (start_choice_ == START_WITH_HANDLER) {
+      if (!HandleControlFrameHeadersComplete(nullptr)) {
+        decode_has_failed_ = true;
+        return false;
+      }
+      total_hpack_bytes = handler_.compressed_header_bytes_parsed();
+    } else {
+      if (!HandleControlFrameHeadersComplete(&total_hpack_bytes)) {
+        decode_has_failed_ = true;
+        return false;
+      }
+    }
+    EXPECT_EQ(total_hpack_bytes, bytes_passed_in_);
+    if (check_decoded_size && start_choice_ == START_WITH_HANDLER) {
+      EXPECT_EQ(handler_.header_bytes_parsed(), SizeOfHeaders(decoded_block()));
+    }
+    return true;
+  }
+
+  bool EncodeAndDecodeDynamicTableSizeUpdates(size_t first, size_t second) {
+    HpackBlockBuilder hbb;
+    hbb.AppendDynamicTableSizeUpdate(first);
+    if (second != first) {
+      hbb.AppendDynamicTableSizeUpdate(second);
+    }
+    return DecodeHeaderBlock(hbb.buffer());
+  }
+
+  const SpdyHeaderBlock& decoded_block() const {
+    if (start_choice_ == START_WITH_HANDLER) {
+      return handler_.decoded_block();
+    } else {
+      return decoder_.decoded_block();
+    }
+  }
+
+  static size_t SizeOfHeaders(const SpdyHeaderBlock& headers) {
+    size_t size = 0;
+    for (const auto& kv : headers) {
+      if (kv.first == kCookieKey) {
+        HpackEncoder::Representations crumbs;
+        HpackEncoderPeer::CookieToCrumbs(kv, &crumbs);
+        for (const auto& crumb : crumbs) {
+          size += crumb.first.size() + crumb.second.size();
+        }
+      } else {
+        size += kv.first.size() + kv.second.size();
+      }
+    }
+    return size;
+  }
+
+  const SpdyHeaderBlock& DecodeBlockExpectingSuccess(SpdyStringPiece str) {
+    EXPECT_TRUE(DecodeHeaderBlock(str));
+    return decoded_block();
+  }
+
+  void expectEntry(size_t index,
+                   size_t size,
+                   const SpdyString& name,
+                   const SpdyString& value) {
+    const HpackStringPair* entry = decoder_peer_.GetTableEntry(index);
+    EXPECT_EQ(name, entry->name) << "index " << index;
+    EXPECT_EQ(value, entry->value);
+    EXPECT_EQ(size, entry->size());
+  }
+
+  SpdyHeaderBlock MakeHeaderBlock(
+      const std::vector<std::pair<SpdyString, SpdyString>>& headers) {
+    SpdyHeaderBlock result;
+    for (const auto& kv : headers) {
+      result.AppendValueOrAddHeader(kv.first, kv.second);
+    }
+    return result;
+  }
+
+  http2::test::Http2Random random_;
+  HpackDecoderAdapter decoder_;
+  test::HpackDecoderAdapterPeer decoder_peer_;
+  TestHeadersHandler handler_;
+  StartChoice start_choice_;
+  bool randomly_split_input_buffer_;
+  bool decode_has_failed_ = false;
+  size_t bytes_passed_in_;
+};
+
+INSTANTIATE_TEST_CASE_P(
+    NoHandler,
+    HpackDecoderAdapterTest,
+    ::testing::Combine(::testing::Values(START_WITHOUT_HANDLER, NO_START),
+                       ::testing::Bool()));
+
+INSTANTIATE_TEST_CASE_P(
+    WithHandler,
+    HpackDecoderAdapterTest,
+    ::testing::Combine(::testing::Values(START_WITH_HANDLER),
+                       ::testing::Bool()));
+
+TEST_P(HpackDecoderAdapterTest,
+       AddHeaderDataWithHandleControlFrameHeadersData) {
+  // The hpack decode buffer size is limited in size. This test verifies that
+  // adding encoded data under that limit is accepted, and data that exceeds the
+  // limit is rejected.
+  HandleControlFrameHeadersStart();
+  const size_t kMaxBufferSizeBytes = 50;
+  const SpdyString a_value = SpdyString(49, 'x');
+  decoder_.set_max_decode_buffer_size_bytes(kMaxBufferSizeBytes);
+  HpackBlockBuilder hbb;
+  hbb.AppendLiteralNameAndValue(HpackEntryType::kNeverIndexedLiteralHeader,
+                                false, "a", false, a_value);
+  const SpdyString& s = hbb.buffer();
+  EXPECT_GT(s.size(), kMaxBufferSizeBytes);
+
+  // Any one in input buffer must not exceed kMaxBufferSizeBytes.
+  EXPECT_TRUE(HandleControlFrameHeadersData(s.substr(0, s.size() / 2)));
+  EXPECT_TRUE(HandleControlFrameHeadersData(s.substr(s.size() / 2)));
+
+  EXPECT_FALSE(HandleControlFrameHeadersData(s));
+  SpdyHeaderBlock expected_block = MakeHeaderBlock({{"a", a_value}});
+  EXPECT_EQ(expected_block, decoded_block());
+}
+
+TEST_P(HpackDecoderAdapterTest, NameTooLong) {
+  // Verify that a name longer than the allowed size generates an error.
+  const size_t kMaxBufferSizeBytes = 50;
+  const SpdyString name = SpdyString(2 * kMaxBufferSizeBytes, 'x');
+  const SpdyString value = "abc";
+
+  decoder_.set_max_decode_buffer_size_bytes(kMaxBufferSizeBytes);
+
+  HpackBlockBuilder hbb;
+  hbb.AppendLiteralNameAndValue(HpackEntryType::kNeverIndexedLiteralHeader,
+                                false, name, false, value);
+
+  const size_t fragment_size = (3 * kMaxBufferSizeBytes) / 2;
+  const SpdyString fragment = hbb.buffer().substr(0, fragment_size);
+
+  HandleControlFrameHeadersStart();
+  EXPECT_FALSE(HandleControlFrameHeadersData(fragment));
+}
+
+TEST_P(HpackDecoderAdapterTest, HeaderTooLongToBuffer) {
+  // Verify that a header longer than the allowed size generates an error if
+  // it isn't all in one input buffer.
+  const SpdyString name = "some-key";
+  const SpdyString value = "some-value";
+  const size_t kMaxBufferSizeBytes = name.size() + value.size() - 2;
+  decoder_.set_max_decode_buffer_size_bytes(kMaxBufferSizeBytes);
+
+  HpackBlockBuilder hbb;
+  hbb.AppendLiteralNameAndValue(HpackEntryType::kNeverIndexedLiteralHeader,
+                                false, name, false, value);
+  const size_t fragment_size = hbb.size() - 1;
+  const SpdyString fragment = hbb.buffer().substr(0, fragment_size);
+
+  HandleControlFrameHeadersStart();
+  EXPECT_FALSE(HandleControlFrameHeadersData(fragment));
+}
+
+// Decode with incomplete data in buffer.
+TEST_P(HpackDecoderAdapterTest, DecodeWithIncompleteData) {
+  HandleControlFrameHeadersStart();
+
+  // No need to wait for more data.
+  EXPECT_TRUE(HandleControlFrameHeadersData("\x82\x85\x82"));
+  std::vector<std::pair<SpdyString, SpdyString>> expected_headers = {
+      {":method", "GET"}, {":path", "/index.html"}, {":method", "GET"}};
+
+  SpdyHeaderBlock expected_block1 = MakeHeaderBlock(expected_headers);
+  EXPECT_EQ(expected_block1, decoded_block());
+
+  // Full and partial headers, won't add partial to the headers.
+  EXPECT_TRUE(
+      HandleControlFrameHeadersData("\x40\x03goo"
+                                    "\x03gar\xbe\x40\x04spam"));
+  expected_headers.push_back({"goo", "gar"});
+  expected_headers.push_back({"goo", "gar"});
+
+  SpdyHeaderBlock expected_block2 = MakeHeaderBlock(expected_headers);
+  EXPECT_EQ(expected_block2, decoded_block());
+
+  // Add the needed data.
+  EXPECT_TRUE(HandleControlFrameHeadersData("\x04gggs"));
+
+  size_t size = 0;
+  EXPECT_TRUE(HandleControlFrameHeadersComplete(&size));
+  EXPECT_EQ(24u, size);
+
+  expected_headers.push_back({"spam", "gggs"});
+
+  SpdyHeaderBlock expected_block3 = MakeHeaderBlock(expected_headers);
+  EXPECT_EQ(expected_block3, decoded_block());
+}
+
+TEST_P(HpackDecoderAdapterTest, HandleHeaderRepresentation) {
+  // Make sure the decoder is properly initialized.
+  HandleControlFrameHeadersStart();
+  HandleControlFrameHeadersData("");
+
+  // All cookie crumbs are joined.
+  decoder_peer_.HandleHeaderRepresentation("cookie", " part 1");
+  decoder_peer_.HandleHeaderRepresentation("cookie", "part 2 ");
+  decoder_peer_.HandleHeaderRepresentation("cookie", "part3");
+
+  // Already-delimited headers are passed through.
+  decoder_peer_.HandleHeaderRepresentation("passed-through",
+                                           SpdyString("foo\0baz", 7));
+
+  // Other headers are joined on \0. Case matters.
+  decoder_peer_.HandleHeaderRepresentation("joined", "not joined");
+  decoder_peer_.HandleHeaderRepresentation("joineD", "value 1");
+  decoder_peer_.HandleHeaderRepresentation("joineD", "value 2");
+
+  // Empty headers remain empty.
+  decoder_peer_.HandleHeaderRepresentation("empty", "");
+
+  // Joined empty headers work as expected.
+  decoder_peer_.HandleHeaderRepresentation("empty-joined", "");
+  decoder_peer_.HandleHeaderRepresentation("empty-joined", "foo");
+  decoder_peer_.HandleHeaderRepresentation("empty-joined", "");
+  decoder_peer_.HandleHeaderRepresentation("empty-joined", "");
+
+  // Non-contiguous cookie crumb.
+  decoder_peer_.HandleHeaderRepresentation("cookie", " fin!");
+
+  // Finish and emit all headers.
+  decoder_.HandleControlFrameHeadersComplete(nullptr);
+
+  // Resulting decoded headers are in the same order as the inputs.
+  EXPECT_THAT(
+      decoded_block(),
+      ElementsAre(Pair("cookie", " part 1; part 2 ; part3;  fin!"),
+                  Pair("passed-through", SpdyStringPiece("foo\0baz", 7)),
+                  Pair("joined", "not joined"),
+                  Pair("joineD", SpdyStringPiece("value 1\0value 2", 15)),
+                  Pair("empty", ""),
+                  Pair("empty-joined", SpdyStringPiece("\0foo\0\0", 6))));
+}
+
+// Decoding indexed static table field should work.
+TEST_P(HpackDecoderAdapterTest, IndexedHeaderStatic) {
+  // Reference static table entries #2 and #5.
+  const SpdyHeaderBlock& header_set1 = DecodeBlockExpectingSuccess("\x82\x85");
+  SpdyHeaderBlock expected_header_set1;
+  expected_header_set1[":method"] = "GET";
+  expected_header_set1[":path"] = "/index.html";
+  EXPECT_EQ(expected_header_set1, header_set1);
+
+  // Reference static table entry #2.
+  const SpdyHeaderBlock& header_set2 = DecodeBlockExpectingSuccess("\x82");
+  SpdyHeaderBlock expected_header_set2;
+  expected_header_set2[":method"] = "GET";
+  EXPECT_EQ(expected_header_set2, header_set2);
+}
+
+TEST_P(HpackDecoderAdapterTest, IndexedHeaderDynamic) {
+  // First header block: add an entry to header table.
+  const SpdyHeaderBlock& header_set1 = DecodeBlockExpectingSuccess(
+      "\x40\x03"
+      "foo"
+      "\x03"
+      "bar");
+  SpdyHeaderBlock expected_header_set1;
+  expected_header_set1["foo"] = "bar";
+  EXPECT_EQ(expected_header_set1, header_set1);
+
+  // Second header block: add another entry to header table.
+  const SpdyHeaderBlock& header_set2 = DecodeBlockExpectingSuccess(
+      "\xbe\x40\x04"
+      "spam"
+      "\x04"
+      "eggs");
+  SpdyHeaderBlock expected_header_set2;
+  expected_header_set2["foo"] = "bar";
+  expected_header_set2["spam"] = "eggs";
+  EXPECT_EQ(expected_header_set2, header_set2);
+
+  // Third header block: refer to most recently added entry.
+  const SpdyHeaderBlock& header_set3 = DecodeBlockExpectingSuccess("\xbe");
+  SpdyHeaderBlock expected_header_set3;
+  expected_header_set3["spam"] = "eggs";
+  EXPECT_EQ(expected_header_set3, header_set3);
+}
+
+// Test a too-large indexed header.
+TEST_P(HpackDecoderAdapterTest, InvalidIndexedHeader) {
+  // High-bit set, and a prefix of one more than the number of static entries.
+  EXPECT_FALSE(DecodeHeaderBlock("\xbe"));
+}
+
+TEST_P(HpackDecoderAdapterTest, ContextUpdateMaximumSize) {
+  EXPECT_EQ(kDefaultHeaderTableSizeSetting,
+            decoder_peer_.header_table_size_limit());
+  SpdyString input;
+  {
+    // Maximum-size update with size 126. Succeeds.
+    HpackOutputStream output_stream;
+    output_stream.AppendPrefix(kHeaderTableSizeUpdateOpcode);
+    output_stream.AppendUint32(126);
+
+    output_stream.TakeString(&input);
+    EXPECT_TRUE(DecodeHeaderBlock(SpdyStringPiece(input)));
+    EXPECT_EQ(126u, decoder_peer_.header_table_size_limit());
+  }
+  {
+    // Maximum-size update with kDefaultHeaderTableSizeSetting. Succeeds.
+    HpackOutputStream output_stream;
+    output_stream.AppendPrefix(kHeaderTableSizeUpdateOpcode);
+    output_stream.AppendUint32(kDefaultHeaderTableSizeSetting);
+
+    output_stream.TakeString(&input);
+    EXPECT_TRUE(DecodeHeaderBlock(SpdyStringPiece(input)));
+    EXPECT_EQ(kDefaultHeaderTableSizeSetting,
+              decoder_peer_.header_table_size_limit());
+  }
+  {
+    // Maximum-size update with kDefaultHeaderTableSizeSetting + 1. Fails.
+    HpackOutputStream output_stream;
+    output_stream.AppendPrefix(kHeaderTableSizeUpdateOpcode);
+    output_stream.AppendUint32(kDefaultHeaderTableSizeSetting + 1);
+
+    output_stream.TakeString(&input);
+    EXPECT_FALSE(DecodeHeaderBlock(SpdyStringPiece(input)));
+    EXPECT_EQ(kDefaultHeaderTableSizeSetting,
+              decoder_peer_.header_table_size_limit());
+  }
+}
+
+// Two HeaderTableSizeUpdates may appear at the beginning of the block
+TEST_P(HpackDecoderAdapterTest, TwoTableSizeUpdates) {
+  SpdyString input;
+  {
+    // Should accept two table size updates, update to second one
+    HpackOutputStream output_stream;
+    output_stream.AppendPrefix(kHeaderTableSizeUpdateOpcode);
+    output_stream.AppendUint32(0);
+    output_stream.AppendPrefix(kHeaderTableSizeUpdateOpcode);
+    output_stream.AppendUint32(122);
+
+    output_stream.TakeString(&input);
+    EXPECT_TRUE(DecodeHeaderBlock(SpdyStringPiece(input)));
+    EXPECT_EQ(122u, decoder_peer_.header_table_size_limit());
+  }
+}
+
+// Three HeaderTableSizeUpdates should result in an error
+TEST_P(HpackDecoderAdapterTest, ThreeTableSizeUpdatesError) {
+  SpdyString input;
+  {
+    // Should reject three table size updates, update to second one
+    HpackOutputStream output_stream;
+    output_stream.AppendPrefix(kHeaderTableSizeUpdateOpcode);
+    output_stream.AppendUint32(5);
+    output_stream.AppendPrefix(kHeaderTableSizeUpdateOpcode);
+    output_stream.AppendUint32(10);
+    output_stream.AppendPrefix(kHeaderTableSizeUpdateOpcode);
+    output_stream.AppendUint32(15);
+
+    output_stream.TakeString(&input);
+
+    EXPECT_FALSE(DecodeHeaderBlock(SpdyStringPiece(input)));
+    EXPECT_EQ(10u, decoder_peer_.header_table_size_limit());
+  }
+}
+
+// HeaderTableSizeUpdates may only appear at the beginning of the block
+// Any other updates should result in an error
+TEST_P(HpackDecoderAdapterTest, TableSizeUpdateSecondError) {
+  SpdyString input;
+  {
+    // Should reject a table size update appearing after a different entry
+    // The table size should remain as the default
+    HpackOutputStream output_stream;
+    output_stream.AppendBytes("\x82\x85");
+    output_stream.AppendPrefix(kHeaderTableSizeUpdateOpcode);
+    output_stream.AppendUint32(123);
+
+    output_stream.TakeString(&input);
+
+    EXPECT_FALSE(DecodeHeaderBlock(SpdyStringPiece(input)));
+    EXPECT_EQ(kDefaultHeaderTableSizeSetting,
+              decoder_peer_.header_table_size_limit());
+  }
+}
+
+// HeaderTableSizeUpdates may only appear at the beginning of the block
+// Any other updates should result in an error
+TEST_P(HpackDecoderAdapterTest, TableSizeUpdateFirstThirdError) {
+  SpdyString input;
+  {
+    // Should reject the second table size update
+    // if a different entry appears after the first update
+    // The table size should update to the first but not the second
+    HpackOutputStream output_stream;
+    output_stream.AppendPrefix(kHeaderTableSizeUpdateOpcode);
+    output_stream.AppendUint32(60);
+    output_stream.AppendBytes("\x82\x85");
+    output_stream.AppendPrefix(kHeaderTableSizeUpdateOpcode);
+    output_stream.AppendUint32(125);
+
+    output_stream.TakeString(&input);
+
+    EXPECT_FALSE(DecodeHeaderBlock(SpdyStringPiece(input)));
+    EXPECT_EQ(60u, decoder_peer_.header_table_size_limit());
+  }
+}
+
+// Decoding two valid encoded literal headers with no indexing should
+// work.
+TEST_P(HpackDecoderAdapterTest, LiteralHeaderNoIndexing) {
+  // First header with indexed name, second header with string literal
+  // name.
+  const char input[] = "\x04\x0c/sample/path\x00\x06:path2\x0e/sample/path/2";
+  const SpdyHeaderBlock& header_set = DecodeBlockExpectingSuccess(
+      SpdyStringPiece(input, SPDY_ARRAYSIZE(input) - 1));
+
+  SpdyHeaderBlock expected_header_set;
+  expected_header_set[":path"] = "/sample/path";
+  expected_header_set[":path2"] = "/sample/path/2";
+  EXPECT_EQ(expected_header_set, header_set);
+}
+
+// Decoding two valid encoded literal headers with incremental
+// indexing and string literal names should work.
+TEST_P(HpackDecoderAdapterTest, LiteralHeaderIncrementalIndexing) {
+  const char input[] = "\x44\x0c/sample/path\x40\x06:path2\x0e/sample/path/2";
+  const SpdyHeaderBlock& header_set = DecodeBlockExpectingSuccess(
+      SpdyStringPiece(input, SPDY_ARRAYSIZE(input) - 1));
+
+  SpdyHeaderBlock expected_header_set;
+  expected_header_set[":path"] = "/sample/path";
+  expected_header_set[":path2"] = "/sample/path/2";
+  EXPECT_EQ(expected_header_set, header_set);
+}
+
+TEST_P(HpackDecoderAdapterTest, LiteralHeaderWithIndexingInvalidNameIndex) {
+  decoder_.ApplyHeaderTableSizeSetting(0);
+  EXPECT_TRUE(EncodeAndDecodeDynamicTableSizeUpdates(0, 0));
+
+  // Name is the last static index. Works.
+  EXPECT_TRUE(DecodeHeaderBlock(SpdyStringPiece("\x7d\x03ooo")));
+  // Name is one beyond the last static index. Fails.
+  EXPECT_FALSE(DecodeHeaderBlock(SpdyStringPiece("\x7e\x03ooo")));
+}
+
+TEST_P(HpackDecoderAdapterTest, LiteralHeaderNoIndexingInvalidNameIndex) {
+  // Name is the last static index. Works.
+  EXPECT_TRUE(DecodeHeaderBlock(SpdyStringPiece("\x0f\x2e\x03ooo")));
+  // Name is one beyond the last static index. Fails.
+  EXPECT_FALSE(DecodeHeaderBlock(SpdyStringPiece("\x0f\x2f\x03ooo")));
+}
+
+TEST_P(HpackDecoderAdapterTest, LiteralHeaderNeverIndexedInvalidNameIndex) {
+  // Name is the last static index. Works.
+  EXPECT_TRUE(DecodeHeaderBlock(SpdyStringPiece("\x1f\x2e\x03ooo")));
+  // Name is one beyond the last static index. Fails.
+  EXPECT_FALSE(DecodeHeaderBlock(SpdyStringPiece("\x1f\x2f\x03ooo")));
+}
+
+TEST_P(HpackDecoderAdapterTest, TruncatedIndex) {
+  // Indexed Header, varint for index requires multiple bytes,
+  // but only one provided.
+  EXPECT_FALSE(DecodeHeaderBlock("\xff"));
+}
+
+TEST_P(HpackDecoderAdapterTest, TruncatedHuffmanLiteral) {
+  // Literal value, Huffman encoded, but with the last byte missing (i.e.
+  // drop the final ff shown below).
+  //
+  // 41                                      | == Literal indexed ==
+  //                                         |   Indexed name (idx = 1)
+  //                                         |     :authority
+  // 8c                                      |   Literal value (len = 12)
+  //                                         |     Huffman encoded:
+  // f1e3 c2e5 f23a 6ba0 ab90 f4ff           | .....:k.....
+  //                                         |     Decoded:
+  //                                         | www.example.com
+  //                                         | -> :authority: www.example.com
+
+  SpdyString first = SpdyHexDecode("418cf1e3c2e5f23a6ba0ab90f4ff");
+  EXPECT_TRUE(DecodeHeaderBlock(first));
+  first.pop_back();
+  EXPECT_FALSE(DecodeHeaderBlock(first));
+}
+
+TEST_P(HpackDecoderAdapterTest, HuffmanEOSError) {
+  // Literal value, Huffman encoded, but with an additional ff byte at the end
+  // of the string, i.e. an EOS that is longer than permitted.
+  //
+  // 41                                      | == Literal indexed ==
+  //                                         |   Indexed name (idx = 1)
+  //                                         |     :authority
+  // 8d                                      |   Literal value (len = 13)
+  //                                         |     Huffman encoded:
+  // f1e3 c2e5 f23a 6ba0 ab90 f4ff           | .....:k.....
+  //                                         |     Decoded:
+  //                                         | www.example.com
+  //                                         | -> :authority: www.example.com
+
+  SpdyString first = SpdyHexDecode("418cf1e3c2e5f23a6ba0ab90f4ff");
+  EXPECT_TRUE(DecodeHeaderBlock(first));
+  first = SpdyHexDecode("418df1e3c2e5f23a6ba0ab90f4ffff");
+  EXPECT_FALSE(DecodeHeaderBlock(first));
+}
+
+// Round-tripping the header set from RFC 7541 C.3.1 should work.
+// http://httpwg.org/specs/rfc7541.html#rfc.section.C.3.1
+TEST_P(HpackDecoderAdapterTest, BasicC31) {
+  HpackEncoder encoder(ObtainHpackHuffmanTable());
+
+  SpdyHeaderBlock expected_header_set;
+  expected_header_set[":method"] = "GET";
+  expected_header_set[":scheme"] = "http";
+  expected_header_set[":path"] = "/";
+  expected_header_set[":authority"] = "www.example.com";
+
+  SpdyString encoded_header_set;
+  EXPECT_TRUE(
+      encoder.EncodeHeaderSet(expected_header_set, &encoded_header_set));
+
+  EXPECT_TRUE(DecodeHeaderBlock(encoded_header_set));
+  EXPECT_EQ(expected_header_set, decoded_block());
+}
+
+// RFC 7541, Section C.4: Request Examples with Huffman Coding
+// http://httpwg.org/specs/rfc7541.html#rfc.section.C.4
+TEST_P(HpackDecoderAdapterTest, SectionC4RequestHuffmanExamples) {
+  // TODO(jamessynge): Use http2/hpack/tools/hpack_example.h to parse the
+  // example directly, instead of having it as a comment.
+  //
+  // 82                                      | == Indexed - Add ==
+  //                                         |   idx = 2
+  //                                         | -> :method: GET
+  // 86                                      | == Indexed - Add ==
+  //                                         |   idx = 6
+  //                                         | -> :scheme: http
+  // 84                                      | == Indexed - Add ==
+  //                                         |   idx = 4
+  //                                         | -> :path: /
+  // 41                                      | == Literal indexed ==
+  //                                         |   Indexed name (idx = 1)
+  //                                         |     :authority
+  // 8c                                      |   Literal value (len = 12)
+  //                                         |     Huffman encoded:
+  // f1e3 c2e5 f23a 6ba0 ab90 f4ff           | .....:k.....
+  //                                         |     Decoded:
+  //                                         | www.example.com
+  //                                         | -> :authority: www.example.com
+  SpdyString first = SpdyHexDecode("828684418cf1e3c2e5f23a6ba0ab90f4ff");
+  const SpdyHeaderBlock& first_header_set = DecodeBlockExpectingSuccess(first);
+
+  EXPECT_THAT(first_header_set,
+              ElementsAre(
+                  // clang-format off
+      Pair(":method", "GET"),
+      Pair(":scheme", "http"),
+      Pair(":path", "/"),
+      Pair(":authority", "www.example.com")));
+  // clang-format on
+
+  expectEntry(62, 57, ":authority", "www.example.com");
+  EXPECT_EQ(57u, decoder_peer_.current_header_table_size());
+
+  // 82                                      | == Indexed - Add ==
+  //                                         |   idx = 2
+  //                                         | -> :method: GET
+  // 86                                      | == Indexed - Add ==
+  //                                         |   idx = 6
+  //                                         | -> :scheme: http
+  // 84                                      | == Indexed - Add ==
+  //                                         |   idx = 4
+  //                                         | -> :path: /
+  // be                                      | == Indexed - Add ==
+  //                                         |   idx = 62
+  //                                         | -> :authority: www.example.com
+  // 58                                      | == Literal indexed ==
+  //                                         |   Indexed name (idx = 24)
+  //                                         |     cache-control
+  // 86                                      |   Literal value (len = 8)
+  //                                         |     Huffman encoded:
+  // a8eb 1064 9cbf                          | ...d..
+  //                                         |     Decoded:
+  //                                         | no-cache
+  //                                         | -> cache-control: no-cache
+
+  SpdyString second = SpdyHexDecode("828684be5886a8eb10649cbf");
+  const SpdyHeaderBlock& second_header_set =
+      DecodeBlockExpectingSuccess(second);
+
+  EXPECT_THAT(second_header_set,
+              ElementsAre(
+                  // clang-format off
+      Pair(":method", "GET"),
+      Pair(":scheme", "http"),
+      Pair(":path", "/"),
+      Pair(":authority", "www.example.com"),
+      Pair("cache-control", "no-cache")));
+  // clang-format on
+
+  expectEntry(62, 53, "cache-control", "no-cache");
+  expectEntry(63, 57, ":authority", "www.example.com");
+  EXPECT_EQ(110u, decoder_peer_.current_header_table_size());
+
+  // 82                                      | == Indexed - Add ==
+  //                                         |   idx = 2
+  //                                         | -> :method: GET
+  // 87                                      | == Indexed - Add ==
+  //                                         |   idx = 7
+  //                                         | -> :scheme: https
+  // 85                                      | == Indexed - Add ==
+  //                                         |   idx = 5
+  //                                         | -> :path: /index.html
+  // bf                                      | == Indexed - Add ==
+  //                                         |   idx = 63
+  //                                         | -> :authority: www.example.com
+  // 40                                      | == Literal indexed ==
+  // 88                                      |   Literal name (len = 10)
+  //                                         |     Huffman encoded:
+  // 25a8 49e9 5ba9 7d7f                     | %.I.[.}.
+  //                                         |     Decoded:
+  //                                         | custom-key
+  // 89                                      |   Literal value (len = 12)
+  //                                         |     Huffman encoded:
+  // 25a8 49e9 5bb8 e8b4 bf                  | %.I.[....
+  //                                         |     Decoded:
+  //                                         | custom-value
+  //                                         | -> custom-key: custom-value
+  SpdyString third =
+      SpdyHexDecode("828785bf408825a849e95ba97d7f8925a849e95bb8e8b4bf");
+  const SpdyHeaderBlock& third_header_set = DecodeBlockExpectingSuccess(third);
+
+  EXPECT_THAT(
+      third_header_set,
+      ElementsAre(
+          // clang-format off
+      Pair(":method", "GET"),
+      Pair(":scheme", "https"),
+      Pair(":path", "/index.html"),
+      Pair(":authority", "www.example.com"),
+      Pair("custom-key", "custom-value")));
+  // clang-format on
+
+  expectEntry(62, 54, "custom-key", "custom-value");
+  expectEntry(63, 53, "cache-control", "no-cache");
+  expectEntry(64, 57, ":authority", "www.example.com");
+  EXPECT_EQ(164u, decoder_peer_.current_header_table_size());
+}
+
+// RFC 7541, Section C.6: Response Examples with Huffman Coding
+// http://httpwg.org/specs/rfc7541.html#rfc.section.C.6
+TEST_P(HpackDecoderAdapterTest, SectionC6ResponseHuffmanExamples) {
+  // The example is based on a maximum dynamic table size of 256,
+  // which allows for testing dynamic table evictions.
+  decoder_peer_.set_header_table_size_limit(256);
+
+  // 48                                      | == Literal indexed ==
+  //                                         |   Indexed name (idx = 8)
+  //                                         |     :status
+  // 82                                      |   Literal value (len = 3)
+  //                                         |     Huffman encoded:
+  // 6402                                    | d.
+  //                                         |     Decoded:
+  //                                         | 302
+  //                                         | -> :status: 302
+  // 58                                      | == Literal indexed ==
+  //                                         |   Indexed name (idx = 24)
+  //                                         |     cache-control
+  // 85                                      |   Literal value (len = 7)
+  //                                         |     Huffman encoded:
+  // aec3 771a 4b                            | ..w.K
+  //                                         |     Decoded:
+  //                                         | private
+  //                                         | -> cache-control: private
+  // 61                                      | == Literal indexed ==
+  //                                         |   Indexed name (idx = 33)
+  //                                         |     date
+  // 96                                      |   Literal value (len = 29)
+  //                                         |     Huffman encoded:
+  // d07a be94 1054 d444 a820 0595 040b 8166 | .z...T.D. .....f
+  // e082 a62d 1bff                          | ...-..
+  //                                         |     Decoded:
+  //                                         | Mon, 21 Oct 2013 20:13:21
+  //                                         | GMT
+  //                                         | -> date: Mon, 21 Oct 2013
+  //                                         |   20:13:21 GMT
+  // 6e                                      | == Literal indexed ==
+  //                                         |   Indexed name (idx = 46)
+  //                                         |     location
+  // 91                                      |   Literal value (len = 23)
+  //                                         |     Huffman encoded:
+  // 9d29 ad17 1863 c78f 0b97 c8e9 ae82 ae43 | .)...c.........C
+  // d3                                      | .
+  //                                         |     Decoded:
+  //                                         | https://www.example.com
+  //                                         | -> location: https://www.e
+  //                                         |    xample.com
+
+  SpdyString first = SpdyHexDecode(
+      "488264025885aec3771a4b6196d07abe"
+      "941054d444a8200595040b8166e082a6"
+      "2d1bff6e919d29ad171863c78f0b97c8"
+      "e9ae82ae43d3");
+  const SpdyHeaderBlock& first_header_set = DecodeBlockExpectingSuccess(first);
+
+  EXPECT_THAT(first_header_set,
+              ElementsAre(
+                  // clang-format off
+      Pair(":status", "302"),
+      Pair("cache-control", "private"),
+      Pair("date", "Mon, 21 Oct 2013 20:13:21 GMT"),
+      Pair("location", "https://www.example.com")));
+  // clang-format on
+
+  expectEntry(62, 63, "location", "https://www.example.com");
+  expectEntry(63, 65, "date", "Mon, 21 Oct 2013 20:13:21 GMT");
+  expectEntry(64, 52, "cache-control", "private");
+  expectEntry(65, 42, ":status", "302");
+  EXPECT_EQ(222u, decoder_peer_.current_header_table_size());
+
+  // 48                                      | == Literal indexed ==
+  //                                         |   Indexed name (idx = 8)
+  //                                         |     :status
+  // 83                                      |   Literal value (len = 3)
+  //                                         |     Huffman encoded:
+  // 640e ff                                 | d..
+  //                                         |     Decoded:
+  //                                         | 307
+  //                                         | - evict: :status: 302
+  //                                         | -> :status: 307
+  // c1                                      | == Indexed - Add ==
+  //                                         |   idx = 65
+  //                                         | -> cache-control: private
+  // c0                                      | == Indexed - Add ==
+  //                                         |   idx = 64
+  //                                         | -> date: Mon, 21 Oct 2013
+  //                                         |   20:13:21 GMT
+  // bf                                      | == Indexed - Add ==
+  //                                         |   idx = 63
+  //                                         | -> location:
+  //                                         |   https://www.example.com
+  SpdyString second = SpdyHexDecode("4883640effc1c0bf");
+  const SpdyHeaderBlock& second_header_set =
+      DecodeBlockExpectingSuccess(second);
+
+  EXPECT_THAT(second_header_set,
+              ElementsAre(
+                  // clang-format off
+      Pair(":status", "307"),
+      Pair("cache-control", "private"),
+      Pair("date", "Mon, 21 Oct 2013 20:13:21 GMT"),
+      Pair("location", "https://www.example.com")));
+  // clang-format on
+
+  expectEntry(62, 42, ":status", "307");
+  expectEntry(63, 63, "location", "https://www.example.com");
+  expectEntry(64, 65, "date", "Mon, 21 Oct 2013 20:13:21 GMT");
+  expectEntry(65, 52, "cache-control", "private");
+  EXPECT_EQ(222u, decoder_peer_.current_header_table_size());
+
+  // 88                                      | == Indexed - Add ==
+  //                                         |   idx = 8
+  //                                         | -> :status: 200
+  // c1                                      | == Indexed - Add ==
+  //                                         |   idx = 65
+  //                                         | -> cache-control: private
+  // 61                                      | == Literal indexed ==
+  //                                         |   Indexed name (idx = 33)
+  //                                         |     date
+  // 96                                      |   Literal value (len = 22)
+  //                                         |     Huffman encoded:
+  // d07a be94 1054 d444 a820 0595 040b 8166 | .z...T.D. .....f
+  // e084 a62d 1bff                          | ...-..
+  //                                         |     Decoded:
+  //                                         | Mon, 21 Oct 2013 20:13:22
+  //                                         | GMT
+  //                                         | - evict: cache-control:
+  //                                         |   private
+  //                                         | -> date: Mon, 21 Oct 2013
+  //                                         |   20:13:22 GMT
+  // c0                                      | == Indexed - Add ==
+  //                                         |   idx = 64
+  //                                         | -> location:
+  //                                         |    https://www.example.com
+  // 5a                                      | == Literal indexed ==
+  //                                         |   Indexed name (idx = 26)
+  //                                         |     content-encoding
+  // 83                                      |   Literal value (len = 3)
+  //                                         |     Huffman encoded:
+  // 9bd9 ab                                 | ...
+  //                                         |     Decoded:
+  //                                         | gzip
+  //                                         | - evict: date: Mon, 21 Oct
+  //                                         |    2013 20:13:21 GMT
+  //                                         | -> content-encoding: gzip
+  // 77                                      | == Literal indexed ==
+  //                                         |   Indexed name (idx = 55)
+  //                                         |     set-cookie
+  // ad                                      |   Literal value (len = 45)
+  //                                         |     Huffman encoded:
+  // 94e7 821d d7f2 e6c7 b335 dfdf cd5b 3960 | .........5...[9`
+  // d5af 2708 7f36 72c1 ab27 0fb5 291f 9587 | ..'..6r..'..)...
+  // 3160 65c0 03ed 4ee5 b106 3d50 07        | 1`e...N...=P.
+  //                                         |     Decoded:
+  //                                         | foo=ASDJKHQKBZXOQWEOPIUAXQ
+  //                                         | WEOIU; max-age=3600; versi
+  //                                         | on=1
+  //                                         | - evict: location:
+  //                                         |   https://www.example.com
+  //                                         | - evict: :status: 307
+  //                                         | -> set-cookie: foo=ASDJKHQ
+  //                                         |   KBZXOQWEOPIUAXQWEOIU;
+  //                                         |   max-age=3600; version=1
+  SpdyString third = SpdyHexDecode(
+      "88c16196d07abe941054d444a8200595"
+      "040b8166e084a62d1bffc05a839bd9ab"
+      "77ad94e7821dd7f2e6c7b335dfdfcd5b"
+      "3960d5af27087f3672c1ab270fb5291f"
+      "9587316065c003ed4ee5b1063d5007");
+  const SpdyHeaderBlock& third_header_set = DecodeBlockExpectingSuccess(third);
+
+  EXPECT_THAT(third_header_set,
+              ElementsAre(
+                  // clang-format off
+      Pair(":status", "200"),
+      Pair("cache-control", "private"),
+      Pair("date", "Mon, 21 Oct 2013 20:13:22 GMT"),
+      Pair("location", "https://www.example.com"),
+      Pair("content-encoding", "gzip"),
+      Pair("set-cookie", "foo=ASDJKHQKBZXOQWEOPIUAXQWEOIU;"
+           " max-age=3600; version=1")));
+  // clang-format on
+
+  expectEntry(62, 98, "set-cookie",
+              "foo=ASDJKHQKBZXOQWEOPIUAXQWEOIU;"
+              " max-age=3600; version=1");
+  expectEntry(63, 52, "content-encoding", "gzip");
+  expectEntry(64, 65, "date", "Mon, 21 Oct 2013 20:13:22 GMT");
+  EXPECT_EQ(215u, decoder_peer_.current_header_table_size());
+}
+
+// Regression test: Found that entries with dynamic indexed names and literal
+// values caused "use after free" MSAN failures if the name was evicted as it
+// was being re-used.
+TEST_P(HpackDecoderAdapterTest, ReuseNameOfEvictedEntry) {
+  // Each entry is measured as 32 bytes plus the sum of the lengths of the name
+  // and the value. Set the size big enough for at most one entry, and a fairly
+  // small one at that (31 ASCII characters).
+  decoder_.ApplyHeaderTableSizeSetting(63);
+
+  HpackBlockBuilder hbb;
+  hbb.AppendDynamicTableSizeUpdate(0);
+  hbb.AppendDynamicTableSizeUpdate(63);
+
+  const SpdyStringPiece name("some-name");
+  const SpdyStringPiece value1("some-value");
+  const SpdyStringPiece value2("another-value");
+  const SpdyStringPiece value3("yet-another-value");
+
+  // Add an entry that will become the first in the dynamic table, entry 62.
+  hbb.AppendLiteralNameAndValue(HpackEntryType::kIndexedLiteralHeader, false,
+                                name, false, value1);
+
+  // Confirm that entry has been added by re-using it.
+  hbb.AppendIndexedHeader(62);
+
+  // Add another entry referring to the name of the first. This will evict the
+  // first.
+  hbb.AppendNameIndexAndLiteralValue(HpackEntryType::kIndexedLiteralHeader, 62,
+                                     false, value2);
+
+  // Confirm that entry has been added by re-using it.
+  hbb.AppendIndexedHeader(62);
+
+  // Add another entry referring to the name of the second. This will evict the
+  // second.
+  hbb.AppendNameIndexAndLiteralValue(HpackEntryType::kIndexedLiteralHeader, 62,
+                                     false, value3);
+
+  // Confirm that entry has been added by re-using it.
+  hbb.AppendIndexedHeader(62);
+
+  // Can't have DecodeHeaderBlock do the default check for size of the decoded
+  // data because SpdyHeaderBlock will join multiple headers with the same
+  // name into a single entry, thus we won't see repeated occurrences of the
+  // name, instead seeing separators between values.
+  EXPECT_TRUE(DecodeHeaderBlock(hbb.buffer(), kNoCheckDecodedSize));
+
+  SpdyHeaderBlock expected_header_set;
+  expected_header_set.AppendValueOrAddHeader(name, value1);
+  expected_header_set.AppendValueOrAddHeader(name, value1);
+  expected_header_set.AppendValueOrAddHeader(name, value2);
+  expected_header_set.AppendValueOrAddHeader(name, value2);
+  expected_header_set.AppendValueOrAddHeader(name, value3);
+  expected_header_set.AppendValueOrAddHeader(name, value3);
+
+  // SpdyHeaderBlock stores these 6 strings as '\0' separated values.
+  // Make sure that is what happened.
+  SpdyString joined_values = expected_header_set[name].as_string();
+  EXPECT_EQ(joined_values.size(),
+            2 * value1.size() + 2 * value2.size() + 2 * value3.size() + 5);
+
+  EXPECT_EQ(expected_header_set, decoded_block());
+
+  if (start_choice_ == START_WITH_HANDLER) {
+    EXPECT_EQ(handler_.header_bytes_parsed(),
+              6 * name.size() + 2 * value1.size() + 2 * value2.size() +
+                  2 * value3.size());
+  }
+}
+
+// Regression test for https://crbug.com/747395.
+TEST_P(HpackDecoderAdapterTest, Cookies) {
+  SpdyHeaderBlock expected_header_set;
+  expected_header_set["cookie"] = "foo; bar";
+
+  EXPECT_TRUE(DecodeHeaderBlock(SpdyHexDecode("608294e76003626172")));
+  EXPECT_EQ(expected_header_set, decoded_block());
+}
+
+}  // namespace
+}  // namespace test
+}  // namespace spdy
diff --git a/spdy/core/hpack/hpack_encoder.cc b/spdy/core/hpack/hpack_encoder.cc
new file mode 100644
index 0000000..a9981b9
--- /dev/null
+++ b/spdy/core/hpack/hpack_encoder.cc
@@ -0,0 +1,365 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_encoder.h"
+
+#include <algorithm>
+#include <limits>
+
+#include "base/logging.h"
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_constants.h"
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_header_table.h"
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_huffman_table.h"
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_output_stream.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_estimate_memory_usage.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_ptr_util.h"
+
+namespace spdy {
+
+class HpackEncoder::RepresentationIterator {
+ public:
+  // |pseudo_headers| and |regular_headers| must outlive the iterator.
+  RepresentationIterator(const Representations& pseudo_headers,
+                         const Representations& regular_headers)
+      : pseudo_begin_(pseudo_headers.begin()),
+        pseudo_end_(pseudo_headers.end()),
+        regular_begin_(regular_headers.begin()),
+        regular_end_(regular_headers.end()) {}
+
+  // |headers| must outlive the iterator.
+  explicit RepresentationIterator(const Representations& headers)
+      : pseudo_begin_(headers.begin()),
+        pseudo_end_(headers.end()),
+        regular_begin_(headers.end()),
+        regular_end_(headers.end()) {}
+
+  bool HasNext() {
+    return pseudo_begin_ != pseudo_end_ || regular_begin_ != regular_end_;
+  }
+
+  const Representation Next() {
+    if (pseudo_begin_ != pseudo_end_) {
+      return *pseudo_begin_++;
+    } else {
+      return *regular_begin_++;
+    }
+  }
+
+ private:
+  Representations::const_iterator pseudo_begin_;
+  Representations::const_iterator pseudo_end_;
+  Representations::const_iterator regular_begin_;
+  Representations::const_iterator regular_end_;
+};
+
+namespace {
+
+// The default header listener.
+void NoOpListener(SpdyStringPiece /*name*/, SpdyStringPiece /*value*/) {}
+
+// The default HPACK indexing policy.
+bool DefaultPolicy(SpdyStringPiece name, SpdyStringPiece /* value */) {
+  if (name.empty()) {
+    return false;
+  }
+  // :authority is always present and rarely changes, and has moderate
+  // length, therefore it makes a lot of sense to index (insert in the
+  // dynamic table).
+  if (name[0] == kPseudoHeaderPrefix) {
+    return name == ":authority";
+  }
+  return true;
+}
+
+}  // namespace
+
+HpackEncoder::HpackEncoder(const HpackHuffmanTable& table)
+    : output_stream_(),
+      huffman_table_(table),
+      min_table_size_setting_received_(std::numeric_limits<size_t>::max()),
+      listener_(NoOpListener),
+      should_index_(DefaultPolicy),
+      enable_compression_(true),
+      should_emit_table_size_(false) {}
+
+HpackEncoder::~HpackEncoder() = default;
+
+bool HpackEncoder::EncodeHeaderSet(const SpdyHeaderBlock& header_set,
+                                   SpdyString* output) {
+  // Separate header set into pseudo-headers and regular headers.
+  Representations pseudo_headers;
+  Representations regular_headers;
+  bool found_cookie = false;
+  for (const auto& header : header_set) {
+    if (!found_cookie && header.first == "cookie") {
+      // Note that there can only be one "cookie" header, because header_set is
+      // a map.
+      found_cookie = true;
+      CookieToCrumbs(header, &regular_headers);
+    } else if (!header.first.empty() &&
+               header.first[0] == kPseudoHeaderPrefix) {
+      DecomposeRepresentation(header, &pseudo_headers);
+    } else {
+      DecomposeRepresentation(header, &regular_headers);
+    }
+  }
+
+  {
+    RepresentationIterator iter(pseudo_headers, regular_headers);
+    EncodeRepresentations(&iter, output);
+  }
+  return true;
+}
+
+void HpackEncoder::ApplyHeaderTableSizeSetting(size_t size_setting) {
+  if (size_setting == header_table_.settings_size_bound()) {
+    return;
+  }
+  if (size_setting < header_table_.settings_size_bound()) {
+    min_table_size_setting_received_ =
+        std::min(size_setting, min_table_size_setting_received_);
+  }
+  header_table_.SetSettingsHeaderTableSize(size_setting);
+  should_emit_table_size_ = true;
+}
+
+size_t HpackEncoder::EstimateMemoryUsage() const {
+  // |huffman_table_| is a singleton. It's accounted for in spdy_session_pool.cc
+  return SpdyEstimateMemoryUsage(header_table_) +
+         SpdyEstimateMemoryUsage(output_stream_);
+}
+
+void HpackEncoder::EncodeRepresentations(RepresentationIterator* iter,
+                                         SpdyString* output) {
+  MaybeEmitTableSize();
+  while (iter->HasNext()) {
+    const auto header = iter->Next();
+    listener_(header.first, header.second);
+    if (enable_compression_) {
+      const HpackEntry* entry =
+          header_table_.GetByNameAndValue(header.first, header.second);
+      if (entry != nullptr) {
+        EmitIndex(entry);
+      } else if (should_index_(header.first, header.second)) {
+        EmitIndexedLiteral(header);
+      } else {
+        EmitNonIndexedLiteral(header);
+      }
+    } else {
+      EmitNonIndexedLiteral(header);
+    }
+  }
+
+  output_stream_.TakeString(output);
+}
+
+void HpackEncoder::EmitIndex(const HpackEntry* entry) {
+  DVLOG(2) << "Emitting index " << header_table_.IndexOf(entry);
+  output_stream_.AppendPrefix(kIndexedOpcode);
+  output_stream_.AppendUint32(header_table_.IndexOf(entry));
+}
+
+void HpackEncoder::EmitIndexedLiteral(const Representation& representation) {
+  DVLOG(2) << "Emitting indexed literal: (" << representation.first << ", "
+           << representation.second << ")";
+  output_stream_.AppendPrefix(kLiteralIncrementalIndexOpcode);
+  EmitLiteral(representation);
+  header_table_.TryAddEntry(representation.first, representation.second);
+}
+
+void HpackEncoder::EmitNonIndexedLiteral(const Representation& representation) {
+  DVLOG(2) << "Emitting nonindexed literal: (" << representation.first << ", "
+           << representation.second << ")";
+  output_stream_.AppendPrefix(kLiteralNoIndexOpcode);
+  output_stream_.AppendUint32(0);
+  EmitString(representation.first);
+  EmitString(representation.second);
+}
+
+void HpackEncoder::EmitLiteral(const Representation& representation) {
+  const HpackEntry* name_entry = header_table_.GetByName(representation.first);
+  if (name_entry != nullptr) {
+    output_stream_.AppendUint32(header_table_.IndexOf(name_entry));
+  } else {
+    output_stream_.AppendUint32(0);
+    EmitString(representation.first);
+  }
+  EmitString(representation.second);
+}
+
+void HpackEncoder::EmitString(SpdyStringPiece str) {
+  size_t encoded_size =
+      enable_compression_ ? huffman_table_.EncodedSize(str) : str.size();
+  if (encoded_size < str.size()) {
+    DVLOG(2) << "Emitted Huffman-encoded string of length " << encoded_size;
+    output_stream_.AppendPrefix(kStringLiteralHuffmanEncoded);
+    output_stream_.AppendUint32(encoded_size);
+    huffman_table_.EncodeString(str, &output_stream_);
+  } else {
+    DVLOG(2) << "Emitted literal string of length " << str.size();
+    output_stream_.AppendPrefix(kStringLiteralIdentityEncoded);
+    output_stream_.AppendUint32(str.size());
+    output_stream_.AppendBytes(str);
+  }
+}
+
+void HpackEncoder::MaybeEmitTableSize() {
+  if (!should_emit_table_size_) {
+    return;
+  }
+  const size_t current_size = CurrentHeaderTableSizeSetting();
+  DVLOG(1) << "MaybeEmitTableSize current_size=" << current_size;
+  DVLOG(1) << "MaybeEmitTableSize min_table_size_setting_received_="
+           << min_table_size_setting_received_;
+  if (min_table_size_setting_received_ < current_size) {
+    output_stream_.AppendPrefix(kHeaderTableSizeUpdateOpcode);
+    output_stream_.AppendUint32(min_table_size_setting_received_);
+  }
+  output_stream_.AppendPrefix(kHeaderTableSizeUpdateOpcode);
+  output_stream_.AppendUint32(current_size);
+  min_table_size_setting_received_ = std::numeric_limits<size_t>::max();
+  should_emit_table_size_ = false;
+}
+
+// static
+void HpackEncoder::CookieToCrumbs(const Representation& cookie,
+                                  Representations* out) {
+  // See Section 8.1.2.5. "Compressing the Cookie Header Field" in the HTTP/2
+  // specification at https://tools.ietf.org/html/draft-ietf-httpbis-http2-14.
+  // Cookie values are split into individually-encoded HPACK representations.
+  SpdyStringPiece cookie_value = cookie.second;
+  // Consume leading and trailing whitespace if present.
+  SpdyStringPiece::size_type first = cookie_value.find_first_not_of(" \t");
+  SpdyStringPiece::size_type last = cookie_value.find_last_not_of(" \t");
+  if (first == SpdyStringPiece::npos) {
+    cookie_value = SpdyStringPiece();
+  } else {
+    cookie_value = cookie_value.substr(first, (last - first) + 1);
+  }
+  for (size_t pos = 0;;) {
+    size_t end = cookie_value.find(";", pos);
+
+    if (end == SpdyStringPiece::npos) {
+      out->push_back(std::make_pair(cookie.first, cookie_value.substr(pos)));
+      break;
+    }
+    out->push_back(
+        std::make_pair(cookie.first, cookie_value.substr(pos, end - pos)));
+
+    // Consume next space if present.
+    pos = end + 1;
+    if (pos != cookie_value.size() && cookie_value[pos] == ' ') {
+      pos++;
+    }
+  }
+}
+
+// static
+void HpackEncoder::DecomposeRepresentation(const Representation& header_field,
+                                           Representations* out) {
+  size_t pos = 0;
+  size_t end = 0;
+  while (end != SpdyStringPiece::npos) {
+    end = header_field.second.find('\0', pos);
+    out->push_back(std::make_pair(
+        header_field.first,
+        header_field.second.substr(
+            pos, end == SpdyStringPiece::npos ? end : end - pos)));
+    pos = end + 1;
+  }
+}
+
+// static
+void HpackEncoder::GatherRepresentation(const Representation& header_field,
+                                        Representations* out) {
+  out->push_back(std::make_pair(header_field.first, header_field.second));
+}
+
+// Iteratively encodes a SpdyHeaderBlock.
+class HpackEncoder::Encoderator : public ProgressiveEncoder {
+ public:
+  Encoderator(const SpdyHeaderBlock& header_set, HpackEncoder* encoder);
+
+  // Encoderator is neither copyable nor movable.
+  Encoderator(const Encoderator&) = delete;
+  Encoderator& operator=(const Encoderator&) = delete;
+
+  // Returns true iff more remains to encode.
+  bool HasNext() const override { return has_next_; }
+
+  // Encodes up to max_encoded_bytes of the current header block into the
+  // given output string.
+  void Next(size_t max_encoded_bytes, SpdyString* output) override;
+
+ private:
+  HpackEncoder* encoder_;
+  std::unique_ptr<RepresentationIterator> header_it_;
+  Representations pseudo_headers_;
+  Representations regular_headers_;
+  bool has_next_;
+};
+
+HpackEncoder::Encoderator::Encoderator(const SpdyHeaderBlock& header_set,
+                                       HpackEncoder* encoder)
+    : encoder_(encoder), has_next_(true) {
+  // Separate header set into pseudo-headers and regular headers.
+  const bool use_compression = encoder_->enable_compression_;
+  bool found_cookie = false;
+  for (const auto& header : header_set) {
+    if (!found_cookie && header.first == "cookie") {
+      // Note that there can only be one "cookie" header, because header_set
+      // is a map.
+      found_cookie = true;
+      CookieToCrumbs(header, &regular_headers_);
+    } else if (!header.first.empty() &&
+               header.first[0] == kPseudoHeaderPrefix) {
+      use_compression ? DecomposeRepresentation(header, &pseudo_headers_)
+                      : GatherRepresentation(header, &pseudo_headers_);
+    } else {
+      use_compression ? DecomposeRepresentation(header, &regular_headers_)
+                      : GatherRepresentation(header, &regular_headers_);
+    }
+  }
+  header_it_ =
+      SpdyMakeUnique<RepresentationIterator>(pseudo_headers_, regular_headers_);
+
+  encoder_->MaybeEmitTableSize();
+}
+
+void HpackEncoder::Encoderator::Next(size_t max_encoded_bytes,
+                                     SpdyString* output) {
+  SPDY_BUG_IF(!has_next_)
+      << "Encoderator::Next called with nothing left to encode.";
+  const bool use_compression = encoder_->enable_compression_;
+
+  // Encode up to max_encoded_bytes of headers.
+  while (header_it_->HasNext() &&
+         encoder_->output_stream_.size() <= max_encoded_bytes) {
+    const Representation header = header_it_->Next();
+    encoder_->listener_(header.first, header.second);
+    if (use_compression) {
+      const HpackEntry* entry = encoder_->header_table_.GetByNameAndValue(
+          header.first, header.second);
+      if (entry != nullptr) {
+        encoder_->EmitIndex(entry);
+      } else if (encoder_->should_index_(header.first, header.second)) {
+        encoder_->EmitIndexedLiteral(header);
+      } else {
+        encoder_->EmitNonIndexedLiteral(header);
+      }
+    } else {
+      encoder_->EmitNonIndexedLiteral(header);
+    }
+  }
+
+  has_next_ = encoder_->output_stream_.size() > max_encoded_bytes;
+  encoder_->output_stream_.BoundedTakeString(max_encoded_bytes, output);
+}
+
+std::unique_ptr<HpackEncoder::ProgressiveEncoder> HpackEncoder::EncodeHeaderSet(
+    const SpdyHeaderBlock& header_set) {
+  return SpdyMakeUnique<Encoderator>(header_set, this);
+}
+
+}  // namespace spdy
diff --git a/spdy/core/hpack/hpack_encoder.h b/spdy/core/hpack/hpack_encoder.h
new file mode 100644
index 0000000..486d536
--- /dev/null
+++ b/spdy/core/hpack/hpack_encoder.h
@@ -0,0 +1,152 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef QUICHE_SPDY_CORE_HPACK_HPACK_ENCODER_H_
+#define QUICHE_SPDY_CORE_HPACK_HPACK_ENCODER_H_
+
+#include <stddef.h>
+
+#include <functional>
+#include <map>
+#include <memory>
+#include <utility>
+#include <vector>
+
+#include "base/macros.h"
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_header_table.h"
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_output_stream.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_protocol.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_export.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string_piece.h"
+
+// An HpackEncoder encodes header sets as outlined in
+// http://tools.ietf.org/html/rfc7541.
+
+namespace spdy {
+
+class HpackHuffmanTable;
+
+namespace test {
+class HpackEncoderPeer;
+}  // namespace test
+
+class SPDY_EXPORT_PRIVATE HpackEncoder {
+ public:
+  using Representation = std::pair<SpdyStringPiece, SpdyStringPiece>;
+  using Representations = std::vector<Representation>;
+
+  // Callers may provide a HeaderListener to be informed of header name-value
+  // pairs processed by this encoder.
+  using HeaderListener = std::function<void(SpdyStringPiece, SpdyStringPiece)>;
+
+  // An indexing policy should return true if the provided header name-value
+  // pair should be inserted into the HPACK dynamic table.
+  using IndexingPolicy = std::function<bool(SpdyStringPiece, SpdyStringPiece)>;
+
+  // |table| is an initialized HPACK Huffman table, having an
+  // externally-managed lifetime which spans beyond HpackEncoder.
+  explicit HpackEncoder(const HpackHuffmanTable& table);
+  HpackEncoder(const HpackEncoder&) = delete;
+  HpackEncoder& operator=(const HpackEncoder&) = delete;
+  ~HpackEncoder();
+
+  // Encodes the given header set into the given string. Returns
+  // whether or not the encoding was successful.
+  bool EncodeHeaderSet(const SpdyHeaderBlock& header_set, SpdyString* output);
+
+  class SPDY_EXPORT_PRIVATE ProgressiveEncoder {
+   public:
+    virtual ~ProgressiveEncoder() {}
+
+    // Returns true iff more remains to encode.
+    virtual bool HasNext() const = 0;
+
+    // Encodes up to max_encoded_bytes of the current header block into the
+    // given output string.
+    virtual void Next(size_t max_encoded_bytes, SpdyString* output) = 0;
+  };
+
+  // Returns a ProgressiveEncoder which must be outlived by both the given
+  // SpdyHeaderBlock and this object.
+  std::unique_ptr<ProgressiveEncoder> EncodeHeaderSet(
+      const SpdyHeaderBlock& header_set);
+
+  // Called upon a change to SETTINGS_HEADER_TABLE_SIZE. Specifically, this
+  // is to be called after receiving (and sending an acknowledgement for) a
+  // SETTINGS_HEADER_TABLE_SIZE update from the remote decoding endpoint.
+  void ApplyHeaderTableSizeSetting(size_t size_setting);
+
+  size_t CurrentHeaderTableSizeSetting() const {
+    return header_table_.settings_size_bound();
+  }
+
+  // This HpackEncoder will use |policy| to determine whether to insert header
+  // name-value pairs into the dynamic table.
+  void SetIndexingPolicy(IndexingPolicy policy) { should_index_ = policy; }
+
+  // |listener| will be invoked for each header name-value pair processed by
+  // this encoder.
+  void SetHeaderListener(HeaderListener listener) { listener_ = listener; }
+
+  void SetHeaderTableDebugVisitor(
+      std::unique_ptr<HpackHeaderTable::DebugVisitorInterface> visitor) {
+    header_table_.set_debug_visitor(std::move(visitor));
+  }
+
+  void DisableCompression() { enable_compression_ = false; }
+
+  // Returns the estimate of dynamically allocated memory in bytes.
+  size_t EstimateMemoryUsage() const;
+
+ private:
+  friend class test::HpackEncoderPeer;
+
+  class RepresentationIterator;
+  class Encoderator;
+
+  // Encodes a sequence of header name-value pairs as a single header block.
+  void EncodeRepresentations(RepresentationIterator* iter, SpdyString* output);
+
+  // Emits a static/dynamic indexed representation (Section 7.1).
+  void EmitIndex(const HpackEntry* entry);
+
+  // Emits a literal representation (Section 7.2).
+  void EmitIndexedLiteral(const Representation& representation);
+  void EmitNonIndexedLiteral(const Representation& representation);
+  void EmitLiteral(const Representation& representation);
+
+  // Emits a Huffman or identity string (whichever is smaller).
+  void EmitString(SpdyStringPiece str);
+
+  // Emits the current dynamic table size if the table size was recently
+  // updated and we have not yet emitted it (Section 6.3).
+  void MaybeEmitTableSize();
+
+  // Crumbles a cookie header into ";" delimited crumbs.
+  static void CookieToCrumbs(const Representation& cookie,
+                             Representations* crumbs_out);
+
+  // Crumbles other header field values at \0 delimiters.
+  static void DecomposeRepresentation(const Representation& header_field,
+                                      Representations* out);
+
+  // Gathers headers without crumbling. Used when compression is not enabled.
+  static void GatherRepresentation(const Representation& header_field,
+                                   Representations* out);
+
+  HpackHeaderTable header_table_;
+  HpackOutputStream output_stream_;
+
+  const HpackHuffmanTable& huffman_table_;
+  size_t min_table_size_setting_received_;
+  HeaderListener listener_;
+  IndexingPolicy should_index_;
+  bool enable_compression_;
+  bool should_emit_table_size_;
+};
+
+}  // namespace spdy
+
+#endif  // QUICHE_SPDY_CORE_HPACK_HPACK_ENCODER_H_
diff --git a/spdy/core/hpack/hpack_encoder_test.cc b/spdy/core/hpack/hpack_encoder_test.cc
new file mode 100644
index 0000000..8ead1c2
--- /dev/null
+++ b/spdy/core/hpack/hpack_encoder_test.cc
@@ -0,0 +1,586 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_encoder.h"
+
+#include <cstdint>
+#include <map>
+
+#include "testing/gmock/include/gmock/gmock.h"
+#include "testing/gtest/include/gtest/gtest.h"
+#include "net/third_party/quiche/src/http2/test_tools/http2_random.h"
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_huffman_table.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_unsafe_arena.h"
+
+namespace spdy {
+
+namespace test {
+
+class HpackHeaderTablePeer {
+ public:
+  explicit HpackHeaderTablePeer(HpackHeaderTable* table) : table_(table) {}
+
+  HpackHeaderTable::EntryTable* dynamic_entries() {
+    return &table_->dynamic_entries_;
+  }
+
+ private:
+  HpackHeaderTable* table_;
+};
+
+class HpackEncoderPeer {
+ public:
+  typedef HpackEncoder::Representation Representation;
+  typedef HpackEncoder::Representations Representations;
+
+  explicit HpackEncoderPeer(HpackEncoder* encoder) : encoder_(encoder) {}
+
+  bool compression_enabled() const { return encoder_->enable_compression_; }
+  HpackHeaderTable* table() { return &encoder_->header_table_; }
+  HpackHeaderTablePeer table_peer() { return HpackHeaderTablePeer(table()); }
+  const HpackHuffmanTable& huffman_table() const {
+    return encoder_->huffman_table_;
+  }
+  void EmitString(SpdyStringPiece str) { encoder_->EmitString(str); }
+  void TakeString(SpdyString* out) { encoder_->output_stream_.TakeString(out); }
+  static void CookieToCrumbs(SpdyStringPiece cookie,
+                             std::vector<SpdyStringPiece>* out) {
+    Representations tmp;
+    HpackEncoder::CookieToCrumbs(std::make_pair("", cookie), &tmp);
+
+    out->clear();
+    for (size_t i = 0; i != tmp.size(); ++i) {
+      out->push_back(tmp[i].second);
+    }
+  }
+  static void DecomposeRepresentation(SpdyStringPiece value,
+                                      std::vector<SpdyStringPiece>* out) {
+    Representations tmp;
+    HpackEncoder::DecomposeRepresentation(std::make_pair("foobar", value),
+                                          &tmp);
+
+    out->clear();
+    for (size_t i = 0; i != tmp.size(); ++i) {
+      out->push_back(tmp[i].second);
+    }
+  }
+
+  // TODO(dahollings): Remove or clean up these methods when deprecating
+  // non-incremental encoding path.
+  static bool EncodeHeaderSet(HpackEncoder* encoder,
+                              const SpdyHeaderBlock& header_set,
+                              SpdyString* output,
+                              bool use_incremental) {
+    if (use_incremental) {
+      return EncodeIncremental(encoder, header_set, output);
+    } else {
+      return encoder->EncodeHeaderSet(header_set, output);
+    }
+  }
+
+  static bool EncodeIncremental(HpackEncoder* encoder,
+                                const SpdyHeaderBlock& header_set,
+                                SpdyString* output) {
+    std::unique_ptr<HpackEncoder::ProgressiveEncoder> encoderator =
+        encoder->EncodeHeaderSet(header_set);
+    SpdyString output_buffer;
+    http2::test::Http2Random random;
+    encoderator->Next(random.UniformInRange(0, 16), &output_buffer);
+    while (encoderator->HasNext()) {
+      SpdyString second_buffer;
+      encoderator->Next(random.UniformInRange(0, 16), &second_buffer);
+      output_buffer.append(second_buffer);
+    }
+    *output = std::move(output_buffer);
+    return true;
+  }
+
+ private:
+  HpackEncoder* encoder_;
+};
+
+}  // namespace test
+
+namespace {
+
+using testing::ElementsAre;
+using testing::Pair;
+
+class HpackEncoderTest : public ::testing::TestWithParam<bool> {
+ protected:
+  typedef test::HpackEncoderPeer::Representations Representations;
+
+  HpackEncoderTest()
+      : encoder_(ObtainHpackHuffmanTable()),
+        peer_(&encoder_),
+        static_(peer_.table()->GetByIndex(1)),
+        headers_storage_(1024 /* block size */) {}
+
+  void SetUp() override {
+    use_incremental_ = GetParam();
+
+    // Populate dynamic entries into the table fixture. For simplicity each
+    // entry has name.size() + value.size() == 10.
+    key_1_ = peer_.table()->TryAddEntry("key1", "value1");
+    key_2_ = peer_.table()->TryAddEntry("key2", "value2");
+    cookie_a_ = peer_.table()->TryAddEntry("cookie", "a=bb");
+    cookie_c_ = peer_.table()->TryAddEntry("cookie", "c=dd");
+
+    // No further insertions may occur without evictions.
+    peer_.table()->SetMaxSize(peer_.table()->size());
+  }
+
+  void SaveHeaders(SpdyStringPiece name, SpdyStringPiece value) {
+    SpdyStringPiece n(headers_storage_.Memdup(name.data(), name.size()),
+                      name.size());
+    SpdyStringPiece v(headers_storage_.Memdup(value.data(), value.size()),
+                      value.size());
+    headers_observed_.push_back(std::make_pair(n, v));
+  }
+
+  void ExpectIndex(size_t index) {
+    expected_.AppendPrefix(kIndexedOpcode);
+    expected_.AppendUint32(index);
+  }
+  void ExpectIndexedLiteral(const HpackEntry* key_entry,
+                            SpdyStringPiece value) {
+    expected_.AppendPrefix(kLiteralIncrementalIndexOpcode);
+    expected_.AppendUint32(IndexOf(key_entry));
+    ExpectString(&expected_, value);
+  }
+  void ExpectIndexedLiteral(SpdyStringPiece name, SpdyStringPiece value) {
+    expected_.AppendPrefix(kLiteralIncrementalIndexOpcode);
+    expected_.AppendUint32(0);
+    ExpectString(&expected_, name);
+    ExpectString(&expected_, value);
+  }
+  void ExpectNonIndexedLiteral(SpdyStringPiece name, SpdyStringPiece value) {
+    expected_.AppendPrefix(kLiteralNoIndexOpcode);
+    expected_.AppendUint32(0);
+    ExpectString(&expected_, name);
+    ExpectString(&expected_, value);
+  }
+  void ExpectString(HpackOutputStream* stream, SpdyStringPiece str) {
+    const HpackHuffmanTable& huffman_table = peer_.huffman_table();
+    size_t encoded_size = peer_.compression_enabled()
+                              ? huffman_table.EncodedSize(str)
+                              : str.size();
+    if (encoded_size < str.size()) {
+      expected_.AppendPrefix(kStringLiteralHuffmanEncoded);
+      expected_.AppendUint32(encoded_size);
+      huffman_table.EncodeString(str, stream);
+    } else {
+      expected_.AppendPrefix(kStringLiteralIdentityEncoded);
+      expected_.AppendUint32(str.size());
+      expected_.AppendBytes(str);
+    }
+  }
+  void ExpectHeaderTableSizeUpdate(uint32_t size) {
+    expected_.AppendPrefix(kHeaderTableSizeUpdateOpcode);
+    expected_.AppendUint32(size);
+  }
+  void CompareWithExpectedEncoding(const SpdyHeaderBlock& header_set) {
+    SpdyString expected_out, actual_out;
+    expected_.TakeString(&expected_out);
+    EXPECT_TRUE(test::HpackEncoderPeer::EncodeHeaderSet(
+        &encoder_, header_set, &actual_out, use_incremental_));
+    EXPECT_EQ(expected_out, actual_out);
+  }
+  size_t IndexOf(const HpackEntry* entry) {
+    return peer_.table()->IndexOf(entry);
+  }
+
+  HpackEncoder encoder_;
+  test::HpackEncoderPeer peer_;
+
+  const HpackEntry* static_;
+  const HpackEntry* key_1_;
+  const HpackEntry* key_2_;
+  const HpackEntry* cookie_a_;
+  const HpackEntry* cookie_c_;
+
+  SpdyUnsafeArena headers_storage_;
+  std::vector<std::pair<SpdyStringPiece, SpdyStringPiece>> headers_observed_;
+
+  HpackOutputStream expected_;
+  bool use_incremental_;
+};
+
+INSTANTIATE_TEST_CASE_P(HpackEncoderTests, HpackEncoderTest, ::testing::Bool());
+
+TEST_P(HpackEncoderTest, SingleDynamicIndex) {
+  encoder_.SetHeaderListener(
+      [this](SpdyStringPiece name, SpdyStringPiece value) {
+        this->SaveHeaders(name, value);
+      });
+
+  ExpectIndex(IndexOf(key_2_));
+
+  SpdyHeaderBlock headers;
+  headers[key_2_->name()] = key_2_->value();
+  CompareWithExpectedEncoding(headers);
+  EXPECT_THAT(headers_observed_,
+              ElementsAre(Pair(key_2_->name(), key_2_->value())));
+}
+
+TEST_P(HpackEncoderTest, SingleStaticIndex) {
+  ExpectIndex(IndexOf(static_));
+
+  SpdyHeaderBlock headers;
+  headers[static_->name()] = static_->value();
+  CompareWithExpectedEncoding(headers);
+}
+
+TEST_P(HpackEncoderTest, SingleStaticIndexTooLarge) {
+  peer_.table()->SetMaxSize(1);  // Also evicts all fixtures.
+  ExpectIndex(IndexOf(static_));
+
+  SpdyHeaderBlock headers;
+  headers[static_->name()] = static_->value();
+  CompareWithExpectedEncoding(headers);
+
+  EXPECT_EQ(0u, peer_.table_peer().dynamic_entries()->size());
+}
+
+TEST_P(HpackEncoderTest, SingleLiteralWithIndexName) {
+  ExpectIndexedLiteral(key_2_, "value3");
+
+  SpdyHeaderBlock headers;
+  headers[key_2_->name()] = "value3";
+  CompareWithExpectedEncoding(headers);
+
+  // A new entry was inserted and added to the reference set.
+  HpackEntry* new_entry = &peer_.table_peer().dynamic_entries()->front();
+  EXPECT_EQ(new_entry->name(), key_2_->name());
+  EXPECT_EQ(new_entry->value(), "value3");
+}
+
+TEST_P(HpackEncoderTest, SingleLiteralWithLiteralName) {
+  ExpectIndexedLiteral("key3", "value3");
+
+  SpdyHeaderBlock headers;
+  headers["key3"] = "value3";
+  CompareWithExpectedEncoding(headers);
+
+  HpackEntry* new_entry = &peer_.table_peer().dynamic_entries()->front();
+  EXPECT_EQ(new_entry->name(), "key3");
+  EXPECT_EQ(new_entry->value(), "value3");
+}
+
+TEST_P(HpackEncoderTest, SingleLiteralTooLarge) {
+  peer_.table()->SetMaxSize(1);  // Also evicts all fixtures.
+
+  ExpectIndexedLiteral("key3", "value3");
+
+  // A header overflowing the header table is still emitted.
+  // The header table is empty.
+  SpdyHeaderBlock headers;
+  headers["key3"] = "value3";
+  CompareWithExpectedEncoding(headers);
+
+  EXPECT_EQ(0u, peer_.table_peer().dynamic_entries()->size());
+}
+
+TEST_P(HpackEncoderTest, EmitThanEvict) {
+  // |key_1_| is toggled and placed into the reference set,
+  // and then immediately evicted by "key3".
+  ExpectIndex(IndexOf(key_1_));
+  ExpectIndexedLiteral("key3", "value3");
+
+  SpdyHeaderBlock headers;
+  headers[key_1_->name()] = key_1_->value();
+  headers["key3"] = "value3";
+  CompareWithExpectedEncoding(headers);
+}
+
+TEST_P(HpackEncoderTest, CookieHeaderIsCrumbled) {
+  ExpectIndex(IndexOf(cookie_a_));
+  ExpectIndex(IndexOf(cookie_c_));
+  ExpectIndexedLiteral(peer_.table()->GetByName("cookie"), "e=ff");
+
+  SpdyHeaderBlock headers;
+  headers["cookie"] = "a=bb; c=dd; e=ff";
+  CompareWithExpectedEncoding(headers);
+}
+
+TEST_P(HpackEncoderTest, StringsDynamicallySelectHuffmanCoding) {
+  // Compactable string. Uses Huffman coding.
+  peer_.EmitString("feedbeef");
+  expected_.AppendPrefix(kStringLiteralHuffmanEncoded);
+  expected_.AppendUint32(6);
+  expected_.AppendBytes("\x94\xA5\x92\x32\x96_");
+
+  // Non-compactable. Uses identity coding.
+  peer_.EmitString("@@@@@@");
+  expected_.AppendPrefix(kStringLiteralIdentityEncoded);
+  expected_.AppendUint32(6);
+  expected_.AppendBytes("@@@@@@");
+
+  SpdyString expected_out, actual_out;
+  expected_.TakeString(&expected_out);
+  peer_.TakeString(&actual_out);
+  EXPECT_EQ(expected_out, actual_out);
+}
+
+TEST_P(HpackEncoderTest, EncodingWithoutCompression) {
+  encoder_.SetHeaderListener(
+      [this](SpdyStringPiece name, SpdyStringPiece value) {
+        this->SaveHeaders(name, value);
+      });
+  encoder_.DisableCompression();
+
+  ExpectNonIndexedLiteral(":path", "/index.html");
+  ExpectNonIndexedLiteral("cookie", "foo=bar");
+  ExpectNonIndexedLiteral("cookie", "baz=bing");
+  ExpectNonIndexedLiteral("hello", "goodbye");
+
+  SpdyHeaderBlock headers;
+  headers[":path"] = "/index.html";
+  headers["cookie"] = "foo=bar; baz=bing";
+  headers["hello"] = "goodbye";
+
+  CompareWithExpectedEncoding(headers);
+
+  EXPECT_THAT(
+      headers_observed_,
+      ElementsAre(Pair(":path", "/index.html"), Pair("cookie", "foo=bar"),
+                  Pair("cookie", "baz=bing"), Pair("hello", "goodbye")));
+}
+
+TEST_P(HpackEncoderTest, MultipleEncodingPasses) {
+  encoder_.SetHeaderListener(
+      [this](SpdyStringPiece name, SpdyStringPiece value) {
+        this->SaveHeaders(name, value);
+      });
+
+  // Pass 1.
+  {
+    SpdyHeaderBlock headers;
+    headers["key1"] = "value1";
+    headers["cookie"] = "a=bb";
+
+    ExpectIndex(IndexOf(key_1_));
+    ExpectIndex(IndexOf(cookie_a_));
+    CompareWithExpectedEncoding(headers);
+  }
+  // Header table is:
+  // 65: key1: value1
+  // 64: key2: value2
+  // 63: cookie: a=bb
+  // 62: cookie: c=dd
+  // Pass 2.
+  {
+    SpdyHeaderBlock headers;
+    headers["key2"] = "value2";
+    headers["cookie"] = "c=dd; e=ff";
+
+    // "key2: value2"
+    ExpectIndex(64);
+    // "cookie: c=dd"
+    ExpectIndex(62);
+    // This cookie evicts |key1| from the dynamic table.
+    ExpectIndexedLiteral(peer_.table()->GetByName("cookie"), "e=ff");
+
+    CompareWithExpectedEncoding(headers);
+  }
+  // Header table is:
+  // 65: key2: value2
+  // 64: cookie: a=bb
+  // 63: cookie: c=dd
+  // 62: cookie: e=ff
+  // Pass 3.
+  {
+    SpdyHeaderBlock headers;
+    headers["key2"] = "value2";
+    headers["cookie"] = "a=bb; b=cc; c=dd";
+
+    // "key2: value2"
+    ExpectIndex(65);
+    // "cookie: a=bb"
+    ExpectIndex(64);
+    // This cookie evicts |key2| from the dynamic table.
+    ExpectIndexedLiteral(peer_.table()->GetByName("cookie"), "b=cc");
+    // "cookie: c=dd"
+    ExpectIndex(64);
+
+    CompareWithExpectedEncoding(headers);
+  }
+
+  // clang-format off
+  EXPECT_THAT(headers_observed_,
+              ElementsAre(Pair("key1", "value1"),
+                          Pair("cookie", "a=bb"),
+                          Pair("key2", "value2"),
+                          Pair("cookie", "c=dd"),
+                          Pair("cookie", "e=ff"),
+                          Pair("key2", "value2"),
+                          Pair("cookie", "a=bb"),
+                          Pair("cookie", "b=cc"),
+                          Pair("cookie", "c=dd")));
+  // clang-format on
+}
+
+TEST_P(HpackEncoderTest, PseudoHeadersFirst) {
+  SpdyHeaderBlock headers;
+  // A pseudo-header that should not be indexed.
+  headers[":path"] = "/spam/eggs.html";
+  // A pseudo-header to be indexed.
+  headers[":authority"] = "www.example.com";
+  // A regular header which precedes ":" alphabetically, should still be encoded
+  // after pseudo-headers.
+  headers["-foo"] = "bar";
+  headers["foo"] = "bar";
+  headers["cookie"] = "c=dd";
+
+  // Headers are indexed in the order in which they were added.
+  // This entry pushes "cookie: a=bb" back to 63.
+  ExpectNonIndexedLiteral(":path", "/spam/eggs.html");
+  ExpectIndexedLiteral(peer_.table()->GetByName(":authority"),
+                       "www.example.com");
+  ExpectIndexedLiteral("-foo", "bar");
+  ExpectIndexedLiteral("foo", "bar");
+  ExpectIndexedLiteral(peer_.table()->GetByName("cookie"), "c=dd");
+  CompareWithExpectedEncoding(headers);
+}
+
+TEST_P(HpackEncoderTest, CookieToCrumbs) {
+  test::HpackEncoderPeer peer(nullptr);
+  std::vector<SpdyStringPiece> out;
+
+  // Leading and trailing whitespace is consumed. A space after ';' is consumed.
+  // All other spaces remain. ';' at beginning and end of string produce empty
+  // crumbs.
+  // See section 8.1.3.4 "Compressing the Cookie Header Field" in the HTTP/2
+  // specification at http://tools.ietf.org/html/draft-ietf-httpbis-http2-11
+  peer.CookieToCrumbs(" foo=1;bar=2 ; bar=3;  bing=4; ", &out);
+  EXPECT_THAT(out, ElementsAre("foo=1", "bar=2 ", "bar=3", " bing=4", ""));
+
+  peer.CookieToCrumbs(";;foo = bar ;; ;baz =bing", &out);
+  EXPECT_THAT(out, ElementsAre("", "", "foo = bar ", "", "", "baz =bing"));
+
+  peer.CookieToCrumbs("baz=bing; foo=bar; baz=bing", &out);
+  EXPECT_THAT(out, ElementsAre("baz=bing", "foo=bar", "baz=bing"));
+
+  peer.CookieToCrumbs("baz=bing", &out);
+  EXPECT_THAT(out, ElementsAre("baz=bing"));
+
+  peer.CookieToCrumbs("", &out);
+  EXPECT_THAT(out, ElementsAre(""));
+
+  peer.CookieToCrumbs("foo;bar; baz;baz;bing;", &out);
+  EXPECT_THAT(out, ElementsAre("foo", "bar", "baz", "baz", "bing", ""));
+
+  peer.CookieToCrumbs(" \t foo=1;bar=2 ; bar=3;\t  ", &out);
+  EXPECT_THAT(out, ElementsAre("foo=1", "bar=2 ", "bar=3", ""));
+
+  peer.CookieToCrumbs(" \t foo=1;bar=2 ; bar=3 \t  ", &out);
+  EXPECT_THAT(out, ElementsAre("foo=1", "bar=2 ", "bar=3"));
+}
+
+TEST_P(HpackEncoderTest, DecomposeRepresentation) {
+  test::HpackEncoderPeer peer(nullptr);
+  std::vector<SpdyStringPiece> out;
+
+  peer.DecomposeRepresentation("", &out);
+  EXPECT_THAT(out, ElementsAre(""));
+
+  peer.DecomposeRepresentation("foobar", &out);
+  EXPECT_THAT(out, ElementsAre("foobar"));
+
+  peer.DecomposeRepresentation(SpdyStringPiece("foo\0bar", 7), &out);
+  EXPECT_THAT(out, ElementsAre("foo", "bar"));
+
+  peer.DecomposeRepresentation(SpdyStringPiece("\0foo\0bar", 8), &out);
+  EXPECT_THAT(out, ElementsAre("", "foo", "bar"));
+
+  peer.DecomposeRepresentation(SpdyStringPiece("foo\0bar\0", 8), &out);
+  EXPECT_THAT(out, ElementsAre("foo", "bar", ""));
+
+  peer.DecomposeRepresentation(SpdyStringPiece("\0foo\0bar\0", 9), &out);
+  EXPECT_THAT(out, ElementsAre("", "foo", "bar", ""));
+}
+
+// Test that encoded headers do not have \0-delimited multiple values, as this
+// became disallowed in HTTP/2 draft-14.
+TEST_P(HpackEncoderTest, CrumbleNullByteDelimitedValue) {
+  SpdyHeaderBlock headers;
+  // A header field to be crumbled: "spam: foo\0bar".
+  headers["spam"] = SpdyString("foo\0bar", 7);
+
+  ExpectIndexedLiteral("spam", "foo");
+  expected_.AppendPrefix(kLiteralIncrementalIndexOpcode);
+  expected_.AppendUint32(62);
+  expected_.AppendPrefix(kStringLiteralIdentityEncoded);
+  expected_.AppendUint32(3);
+  expected_.AppendBytes("bar");
+  CompareWithExpectedEncoding(headers);
+}
+
+TEST_P(HpackEncoderTest, HeaderTableSizeUpdate) {
+  encoder_.ApplyHeaderTableSizeSetting(1024);
+  ExpectHeaderTableSizeUpdate(1024);
+  ExpectIndexedLiteral("key3", "value3");
+
+  SpdyHeaderBlock headers;
+  headers["key3"] = "value3";
+  CompareWithExpectedEncoding(headers);
+
+  HpackEntry* new_entry = &peer_.table_peer().dynamic_entries()->front();
+  EXPECT_EQ(new_entry->name(), "key3");
+  EXPECT_EQ(new_entry->value(), "value3");
+}
+
+TEST_P(HpackEncoderTest, HeaderTableSizeUpdateWithMin) {
+  const size_t starting_size = peer_.table()->settings_size_bound();
+  encoder_.ApplyHeaderTableSizeSetting(starting_size - 2);
+  encoder_.ApplyHeaderTableSizeSetting(starting_size - 1);
+  // We must encode the low watermark, so the peer knows to evict entries
+  // if necessary.
+  ExpectHeaderTableSizeUpdate(starting_size - 2);
+  ExpectHeaderTableSizeUpdate(starting_size - 1);
+  ExpectIndexedLiteral("key3", "value3");
+
+  SpdyHeaderBlock headers;
+  headers["key3"] = "value3";
+  CompareWithExpectedEncoding(headers);
+
+  HpackEntry* new_entry = &peer_.table_peer().dynamic_entries()->front();
+  EXPECT_EQ(new_entry->name(), "key3");
+  EXPECT_EQ(new_entry->value(), "value3");
+}
+
+TEST_P(HpackEncoderTest, HeaderTableSizeUpdateWithExistingSize) {
+  encoder_.ApplyHeaderTableSizeSetting(peer_.table()->settings_size_bound());
+  // No encoded size update.
+  ExpectIndexedLiteral("key3", "value3");
+
+  SpdyHeaderBlock headers;
+  headers["key3"] = "value3";
+  CompareWithExpectedEncoding(headers);
+
+  HpackEntry* new_entry = &peer_.table_peer().dynamic_entries()->front();
+  EXPECT_EQ(new_entry->name(), "key3");
+  EXPECT_EQ(new_entry->value(), "value3");
+}
+
+TEST_P(HpackEncoderTest, HeaderTableSizeUpdatesWithGreaterSize) {
+  const size_t starting_size = peer_.table()->settings_size_bound();
+  encoder_.ApplyHeaderTableSizeSetting(starting_size + 1);
+  encoder_.ApplyHeaderTableSizeSetting(starting_size + 2);
+  // Only a single size update to the final size.
+  ExpectHeaderTableSizeUpdate(starting_size + 2);
+  ExpectIndexedLiteral("key3", "value3");
+
+  SpdyHeaderBlock headers;
+  headers["key3"] = "value3";
+  CompareWithExpectedEncoding(headers);
+
+  HpackEntry* new_entry = &peer_.table_peer().dynamic_entries()->front();
+  EXPECT_EQ(new_entry->name(), "key3");
+  EXPECT_EQ(new_entry->value(), "value3");
+}
+
+}  // namespace
+
+}  // namespace spdy
diff --git a/spdy/core/hpack/hpack_entry.cc b/spdy/core/hpack/hpack_entry.cc
new file mode 100644
index 0000000..90d53e6
--- /dev/null
+++ b/spdy/core/hpack/hpack_entry.cc
@@ -0,0 +1,89 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_entry.h"
+
+#include "base/logging.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_estimate_memory_usage.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string_utils.h"
+
+namespace spdy {
+
+const size_t HpackEntry::kSizeOverhead = 32;
+
+HpackEntry::HpackEntry(SpdyStringPiece name,
+                       SpdyStringPiece value,
+                       bool is_static,
+                       size_t insertion_index)
+    : name_(name.data(), name.size()),
+      value_(value.data(), value.size()),
+      name_ref_(name_),
+      value_ref_(value_),
+      insertion_index_(insertion_index),
+      type_(is_static ? STATIC : DYNAMIC),
+      time_added_(0) {}
+
+HpackEntry::HpackEntry(SpdyStringPiece name, SpdyStringPiece value)
+    : name_ref_(name),
+      value_ref_(value),
+      insertion_index_(0),
+      type_(LOOKUP),
+      time_added_(0) {}
+
+HpackEntry::HpackEntry() : insertion_index_(0), type_(LOOKUP), time_added_(0) {}
+
+HpackEntry::HpackEntry(const HpackEntry& other)
+    : insertion_index_(other.insertion_index_),
+      type_(other.type_),
+      time_added_(0) {
+  if (type_ == LOOKUP) {
+    name_ref_ = other.name_ref_;
+    value_ref_ = other.value_ref_;
+  } else {
+    name_ = other.name_;
+    value_ = other.value_;
+    name_ref_ = SpdyStringPiece(name_.data(), name_.size());
+    value_ref_ = SpdyStringPiece(value_.data(), value_.size());
+  }
+}
+
+HpackEntry& HpackEntry::operator=(const HpackEntry& other) {
+  insertion_index_ = other.insertion_index_;
+  type_ = other.type_;
+  if (type_ == LOOKUP) {
+    name_.clear();
+    value_.clear();
+    name_ref_ = other.name_ref_;
+    value_ref_ = other.value_ref_;
+    return *this;
+  }
+  name_ = other.name_;
+  value_ = other.value_;
+  name_ref_ = SpdyStringPiece(name_.data(), name_.size());
+  value_ref_ = SpdyStringPiece(value_.data(), value_.size());
+  return *this;
+}
+
+HpackEntry::~HpackEntry() = default;
+
+// static
+size_t HpackEntry::Size(SpdyStringPiece name, SpdyStringPiece value) {
+  return name.size() + value.size() + kSizeOverhead;
+}
+size_t HpackEntry::Size() const {
+  return Size(name(), value());
+}
+
+SpdyString HpackEntry::GetDebugString() const {
+  return SpdyStrCat(
+      "{ name: \"", name_ref_, "\", value: \"", value_ref_,
+      "\", index: ", insertion_index_, " ",
+      (IsStatic() ? " static" : (IsLookup() ? " lookup" : " dynamic")), " }");
+}
+
+size_t HpackEntry::EstimateMemoryUsage() const {
+  return SpdyEstimateMemoryUsage(name_) + SpdyEstimateMemoryUsage(value_);
+}
+
+}  // namespace spdy
diff --git a/spdy/core/hpack/hpack_entry.h b/spdy/core/hpack/hpack_entry.h
new file mode 100644
index 0000000..28dee47
--- /dev/null
+++ b/spdy/core/hpack/hpack_entry.h
@@ -0,0 +1,110 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef QUICHE_SPDY_CORE_HPACK_HPACK_ENTRY_H_
+#define QUICHE_SPDY_CORE_HPACK_HPACK_ENTRY_H_
+
+#include <cstddef>
+#include <cstdint>
+
+#include "base/macros.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_export.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string_piece.h"
+
+// All section references below are to
+// http://tools.ietf.org/html/draft-ietf-httpbis-header-compression-08
+
+namespace spdy {
+
+// A structure for an entry in the static table (3.3.1)
+// and the header table (3.3.2).
+class SPDY_EXPORT_PRIVATE HpackEntry {
+ public:
+  // The constant amount added to name().size() and value().size() to
+  // get the size of an HpackEntry as defined in 5.1.
+  static const size_t kSizeOverhead;
+
+  // Creates an entry. Preconditions:
+  // - |is_static| captures whether this entry is a member of the static
+  //   or dynamic header table.
+  // - |insertion_index| is this entry's index in the total set of entries ever
+  //   inserted into the header table (including static entries).
+  //
+  // The combination of |is_static| and |insertion_index| allows an
+  // HpackEntryTable to determine the index of an HpackEntry in O(1) time.
+  // Copies |name| and |value|.
+  HpackEntry(SpdyStringPiece name,
+             SpdyStringPiece value,
+             bool is_static,
+             size_t insertion_index);
+
+  // Create a 'lookup' entry (only) suitable for querying a HpackEntrySet. The
+  // instance InsertionIndex() always returns 0 and IsLookup() returns true.
+  // The memory backing |name| and |value| must outlive this object.
+  HpackEntry(SpdyStringPiece name, SpdyStringPiece value);
+
+  HpackEntry(const HpackEntry& other);
+  HpackEntry& operator=(const HpackEntry& other);
+
+  // Creates an entry with empty name and value. Only defined so that
+  // entries can be stored in STL containers.
+  HpackEntry();
+
+  ~HpackEntry();
+
+  SpdyStringPiece name() const { return name_ref_; }
+  SpdyStringPiece value() const { return value_ref_; }
+
+  // Returns whether this entry is a member of the static (as opposed to
+  // dynamic) table.
+  bool IsStatic() const { return type_ == STATIC; }
+
+  // Returns whether this entry is a lookup-only entry.
+  bool IsLookup() const { return type_ == LOOKUP; }
+
+  // Used to compute the entry's index in the header table.
+  size_t InsertionIndex() const { return insertion_index_; }
+
+  // Returns the size of an entry as defined in 5.1.
+  static size_t Size(SpdyStringPiece name, SpdyStringPiece value);
+  size_t Size() const;
+
+  SpdyString GetDebugString() const;
+
+  int64_t time_added() const { return time_added_; }
+  void set_time_added(int64_t now) { time_added_ = now; }
+
+  // Returns the estimate of dynamically allocated memory in bytes.
+  size_t EstimateMemoryUsage() const;
+
+ private:
+  enum EntryType {
+    LOOKUP,
+    DYNAMIC,
+    STATIC,
+  };
+
+  // These members are not used for LOOKUP entries.
+  SpdyString name_;
+  SpdyString value_;
+
+  // These members are always valid. For DYNAMIC and STATIC entries, they
+  // always point to |name_| and |value_|.
+  SpdyStringPiece name_ref_;
+  SpdyStringPiece value_ref_;
+
+  // The entry's index in the total set of entries ever inserted into the header
+  // table.
+  size_t insertion_index_;
+
+  EntryType type_;
+
+  // For HpackHeaderTable::DebugVisitorInterface
+  int64_t time_added_;
+};
+
+}  // namespace spdy
+
+#endif  // QUICHE_SPDY_CORE_HPACK_HPACK_ENTRY_H_
diff --git a/spdy/core/hpack/hpack_entry_test.cc b/spdy/core/hpack/hpack_entry_test.cc
new file mode 100644
index 0000000..507c851
--- /dev/null
+++ b/spdy/core/hpack/hpack_entry_test.cc
@@ -0,0 +1,122 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_entry.h"
+
+#include "testing/gtest/include/gtest/gtest.h"
+
+namespace spdy {
+
+namespace {
+
+class HpackEntryTest : public ::testing::Test {
+ protected:
+  HpackEntryTest()
+      : name_("header-name"),
+        value_("header value"),
+        total_insertions_(0),
+        table_size_(0) {}
+
+  // These builders maintain the same external table invariants that a "real"
+  // table (ie HpackHeaderTable) would.
+  HpackEntry StaticEntry() {
+    return HpackEntry(name_, value_, true, total_insertions_++);
+  }
+  HpackEntry DynamicEntry() {
+    ++table_size_;
+    size_t index = total_insertions_++;
+    return HpackEntry(name_, value_, false, index);
+  }
+  void DropEntry() { --table_size_; }
+
+  size_t IndexOf(const HpackEntry& entry) const {
+    if (entry.IsStatic()) {
+      return 1 + entry.InsertionIndex() + table_size_;
+    } else {
+      return total_insertions_ - entry.InsertionIndex();
+    }
+  }
+
+  size_t Size() {
+    return name_.size() + value_.size() + HpackEntry::kSizeOverhead;
+  }
+
+  SpdyString name_, value_;
+
+ private:
+  // Referenced by HpackEntry instances.
+  size_t total_insertions_;
+  size_t table_size_;
+};
+
+TEST_F(HpackEntryTest, StaticConstructor) {
+  HpackEntry entry(StaticEntry());
+
+  EXPECT_EQ(name_, entry.name());
+  EXPECT_EQ(value_, entry.value());
+  EXPECT_TRUE(entry.IsStatic());
+  EXPECT_EQ(1u, IndexOf(entry));
+  EXPECT_EQ(Size(), entry.Size());
+}
+
+TEST_F(HpackEntryTest, DynamicConstructor) {
+  HpackEntry entry(DynamicEntry());
+
+  EXPECT_EQ(name_, entry.name());
+  EXPECT_EQ(value_, entry.value());
+  EXPECT_FALSE(entry.IsStatic());
+  EXPECT_EQ(1u, IndexOf(entry));
+  EXPECT_EQ(Size(), entry.Size());
+}
+
+TEST_F(HpackEntryTest, LookupConstructor) {
+  HpackEntry entry(name_, value_);
+
+  EXPECT_EQ(name_, entry.name());
+  EXPECT_EQ(value_, entry.value());
+  EXPECT_FALSE(entry.IsStatic());
+  EXPECT_EQ(0u, IndexOf(entry));
+  EXPECT_EQ(Size(), entry.Size());
+}
+
+TEST_F(HpackEntryTest, DefaultConstructor) {
+  HpackEntry entry;
+
+  EXPECT_TRUE(entry.name().empty());
+  EXPECT_TRUE(entry.value().empty());
+  EXPECT_EQ(HpackEntry::kSizeOverhead, entry.Size());
+}
+
+TEST_F(HpackEntryTest, IndexUpdate) {
+  HpackEntry static1(StaticEntry());
+  HpackEntry static2(StaticEntry());
+
+  EXPECT_EQ(1u, IndexOf(static1));
+  EXPECT_EQ(2u, IndexOf(static2));
+
+  HpackEntry dynamic1(DynamicEntry());
+  HpackEntry dynamic2(DynamicEntry());
+
+  EXPECT_EQ(1u, IndexOf(dynamic2));
+  EXPECT_EQ(2u, IndexOf(dynamic1));
+  EXPECT_EQ(3u, IndexOf(static1));
+  EXPECT_EQ(4u, IndexOf(static2));
+
+  DropEntry();  // Drops |dynamic1|.
+
+  EXPECT_EQ(1u, IndexOf(dynamic2));
+  EXPECT_EQ(2u, IndexOf(static1));
+  EXPECT_EQ(3u, IndexOf(static2));
+
+  HpackEntry dynamic3(DynamicEntry());
+
+  EXPECT_EQ(1u, IndexOf(dynamic3));
+  EXPECT_EQ(2u, IndexOf(dynamic2));
+  EXPECT_EQ(3u, IndexOf(static1));
+  EXPECT_EQ(4u, IndexOf(static2));
+}
+
+}  // namespace
+
+}  // namespace spdy
diff --git a/spdy/core/hpack/hpack_header_table.cc b/spdy/core/hpack/hpack_header_table.cc
new file mode 100644
index 0000000..dbe565f
--- /dev/null
+++ b/spdy/core/hpack/hpack_header_table.cc
@@ -0,0 +1,274 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_header_table.h"
+
+#include <algorithm>
+
+#include "base/logging.h"
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_constants.h"
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_static_table.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_containers.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_estimate_memory_usage.h"
+
+namespace spdy {
+
+size_t HpackHeaderTable::EntryHasher::operator()(
+    const HpackEntry* entry) const {
+  return SpdyHashStringPair(entry->name(), entry->value());
+}
+
+bool HpackHeaderTable::EntriesEq::operator()(const HpackEntry* lhs,
+                                             const HpackEntry* rhs) const {
+  if (lhs == nullptr) {
+    return rhs == nullptr;
+  }
+  if (rhs == nullptr) {
+    return false;
+  }
+  return lhs->name() == rhs->name() && lhs->value() == rhs->value();
+}
+
+HpackHeaderTable::HpackHeaderTable()
+    : static_entries_(ObtainHpackStaticTable().GetStaticEntries()),
+      static_index_(ObtainHpackStaticTable().GetStaticIndex()),
+      static_name_index_(ObtainHpackStaticTable().GetStaticNameIndex()),
+      settings_size_bound_(kDefaultHeaderTableSizeSetting),
+      size_(0),
+      max_size_(kDefaultHeaderTableSizeSetting),
+      total_insertions_(static_entries_.size()) {}
+
+HpackHeaderTable::~HpackHeaderTable() = default;
+
+const HpackEntry* HpackHeaderTable::GetByIndex(size_t index) {
+  if (index == 0) {
+    return nullptr;
+  }
+  index -= 1;
+  if (index < static_entries_.size()) {
+    return &static_entries_[index];
+  }
+  index -= static_entries_.size();
+  if (index < dynamic_entries_.size()) {
+    const HpackEntry* result = &dynamic_entries_[index];
+    if (debug_visitor_ != nullptr) {
+      debug_visitor_->OnUseEntry(*result);
+    }
+    return result;
+  }
+  return nullptr;
+}
+
+const HpackEntry* HpackHeaderTable::GetByName(SpdyStringPiece name) {
+  {
+    auto it = static_name_index_.find(name);
+    if (it != static_name_index_.end()) {
+      return it->second;
+    }
+  }
+  {
+    NameToEntryMap::const_iterator it = dynamic_name_index_.find(name);
+    if (it != dynamic_name_index_.end()) {
+      const HpackEntry* result = it->second;
+      if (debug_visitor_ != nullptr) {
+        debug_visitor_->OnUseEntry(*result);
+      }
+      return result;
+    }
+  }
+  return nullptr;
+}
+
+const HpackEntry* HpackHeaderTable::GetByNameAndValue(SpdyStringPiece name,
+                                                      SpdyStringPiece value) {
+  HpackEntry query(name, value);
+  {
+    auto it = static_index_.find(&query);
+    if (it != static_index_.end()) {
+      return *it;
+    }
+  }
+  {
+    auto it = dynamic_index_.find(&query);
+    if (it != dynamic_index_.end()) {
+      const HpackEntry* result = *it;
+      if (debug_visitor_ != nullptr) {
+        debug_visitor_->OnUseEntry(*result);
+      }
+      return result;
+    }
+  }
+  return nullptr;
+}
+
+size_t HpackHeaderTable::IndexOf(const HpackEntry* entry) const {
+  if (entry->IsLookup()) {
+    return 0;
+  } else if (entry->IsStatic()) {
+    return 1 + entry->InsertionIndex();
+  } else {
+    return total_insertions_ - entry->InsertionIndex() + static_entries_.size();
+  }
+}
+
+void HpackHeaderTable::SetMaxSize(size_t max_size) {
+  CHECK_LE(max_size, settings_size_bound_);
+
+  max_size_ = max_size;
+  if (size_ > max_size_) {
+    Evict(EvictionCountToReclaim(size_ - max_size_));
+    CHECK_LE(size_, max_size_);
+  }
+}
+
+void HpackHeaderTable::SetSettingsHeaderTableSize(size_t settings_size) {
+  settings_size_bound_ = settings_size;
+  SetMaxSize(settings_size_bound_);
+}
+
+void HpackHeaderTable::EvictionSet(SpdyStringPiece name,
+                                   SpdyStringPiece value,
+                                   EntryTable::iterator* begin_out,
+                                   EntryTable::iterator* end_out) {
+  size_t eviction_count = EvictionCountForEntry(name, value);
+  *begin_out = dynamic_entries_.end() - eviction_count;
+  *end_out = dynamic_entries_.end();
+}
+
+size_t HpackHeaderTable::EvictionCountForEntry(SpdyStringPiece name,
+                                               SpdyStringPiece value) const {
+  size_t available_size = max_size_ - size_;
+  size_t entry_size = HpackEntry::Size(name, value);
+
+  if (entry_size <= available_size) {
+    // No evictions are required.
+    return 0;
+  }
+  return EvictionCountToReclaim(entry_size - available_size);
+}
+
+size_t HpackHeaderTable::EvictionCountToReclaim(size_t reclaim_size) const {
+  size_t count = 0;
+  for (auto it = dynamic_entries_.rbegin();
+       it != dynamic_entries_.rend() && reclaim_size != 0; ++it, ++count) {
+    reclaim_size -= std::min(reclaim_size, it->Size());
+  }
+  return count;
+}
+
+void HpackHeaderTable::Evict(size_t count) {
+  for (size_t i = 0; i != count; ++i) {
+    CHECK(!dynamic_entries_.empty());
+    HpackEntry* entry = &dynamic_entries_.back();
+
+    size_ -= entry->Size();
+    auto it = dynamic_index_.find(entry);
+    DCHECK(it != dynamic_index_.end());
+    // Only remove an entry from the index if its insertion index matches;
+    // otherwise, the index refers to another entry with the same name and
+    // value.
+    if ((*it)->InsertionIndex() == entry->InsertionIndex()) {
+      dynamic_index_.erase(it);
+    }
+    auto name_it = dynamic_name_index_.find(entry->name());
+    DCHECK(name_it != dynamic_name_index_.end());
+    // Only remove an entry from the literal index if its insertion index
+    /// matches; otherwise, the index refers to another entry with the same
+    // name.
+    if (name_it->second->InsertionIndex() == entry->InsertionIndex()) {
+      dynamic_name_index_.erase(name_it);
+    }
+    dynamic_entries_.pop_back();
+  }
+}
+
+const HpackEntry* HpackHeaderTable::TryAddEntry(SpdyStringPiece name,
+                                                SpdyStringPiece value) {
+  Evict(EvictionCountForEntry(name, value));
+
+  size_t entry_size = HpackEntry::Size(name, value);
+  if (entry_size > (max_size_ - size_)) {
+    // Entire table has been emptied, but there's still insufficient room.
+    DCHECK(dynamic_entries_.empty());
+    DCHECK_EQ(0u, size_);
+    return nullptr;
+  }
+  dynamic_entries_.push_front(HpackEntry(name, value,
+                                         false,  // is_static
+                                         total_insertions_));
+  HpackEntry* new_entry = &dynamic_entries_.front();
+  auto index_result = dynamic_index_.insert(new_entry);
+  if (!index_result.second) {
+    // An entry with the same name and value already exists in the dynamic
+    // index. We should replace it with the newly added entry.
+    DVLOG(1) << "Found existing entry: "
+             << (*index_result.first)->GetDebugString()
+             << " replacing with: " << new_entry->GetDebugString();
+    DCHECK_GT(new_entry->InsertionIndex(),
+              (*index_result.first)->InsertionIndex());
+    dynamic_index_.erase(index_result.first);
+    CHECK(dynamic_index_.insert(new_entry).second);
+  }
+
+  auto name_result =
+      dynamic_name_index_.insert(std::make_pair(new_entry->name(), new_entry));
+  if (!name_result.second) {
+    // An entry with the same name already exists in the dynamic index. We
+    // should replace it with the newly added entry.
+    DVLOG(1) << "Found existing entry: "
+             << name_result.first->second->GetDebugString()
+             << " replacing with: " << new_entry->GetDebugString();
+    DCHECK_GT(new_entry->InsertionIndex(),
+              name_result.first->second->InsertionIndex());
+    dynamic_name_index_.erase(name_result.first);
+    auto insert_result = dynamic_name_index_.insert(
+        std::make_pair(new_entry->name(), new_entry));
+    CHECK(insert_result.second);
+  }
+
+  size_ += entry_size;
+  ++total_insertions_;
+  if (debug_visitor_ != nullptr) {
+    // Call |debug_visitor_->OnNewEntry()| to get the current time.
+    HpackEntry& entry = dynamic_entries_.front();
+    entry.set_time_added(debug_visitor_->OnNewEntry(entry));
+    DVLOG(2) << "HpackHeaderTable::OnNewEntry: name=" << entry.name()
+             << ",  value=" << entry.value()
+             << ",  insert_index=" << entry.InsertionIndex()
+             << ",  time_added=" << entry.time_added();
+  }
+
+  return &dynamic_entries_.front();
+}
+
+void HpackHeaderTable::DebugLogTableState() const {
+  DVLOG(2) << "Dynamic table:";
+  for (auto it = dynamic_entries_.begin(); it != dynamic_entries_.end(); ++it) {
+    DVLOG(2) << "  " << it->GetDebugString();
+  }
+  DVLOG(2) << "Full Static Index:";
+  for (const auto* entry : static_index_) {
+    DVLOG(2) << "  " << entry->GetDebugString();
+  }
+  DVLOG(2) << "Full Static Name Index:";
+  for (const auto it : static_name_index_) {
+    DVLOG(2) << "  " << it.first << ": " << it.second->GetDebugString();
+  }
+  DVLOG(2) << "Full Dynamic Index:";
+  for (const auto* entry : dynamic_index_) {
+    DVLOG(2) << "  " << entry->GetDebugString();
+  }
+  DVLOG(2) << "Full Dynamic Name Index:";
+  for (const auto it : dynamic_name_index_) {
+    DVLOG(2) << "  " << it.first << ": " << it.second->GetDebugString();
+  }
+}
+
+size_t HpackHeaderTable::EstimateMemoryUsage() const {
+  return SpdyEstimateMemoryUsage(dynamic_entries_) +
+         SpdyEstimateMemoryUsage(dynamic_index_) +
+         SpdyEstimateMemoryUsage(dynamic_name_index_);
+}
+
+}  // namespace spdy
diff --git a/spdy/core/hpack/hpack_header_table.h b/spdy/core/hpack/hpack_header_table.h
new file mode 100644
index 0000000..e85edb7
--- /dev/null
+++ b/spdy/core/hpack/hpack_header_table.h
@@ -0,0 +1,180 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef QUICHE_SPDY_CORE_HPACK_HPACK_HEADER_TABLE_H_
+#define QUICHE_SPDY_CORE_HPACK_HPACK_HEADER_TABLE_H_
+
+#include <cstddef>
+#include <cstdint>
+#include <deque>
+#include <memory>
+
+#include "base/macros.h"
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_entry.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_containers.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_export.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_macros.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string_piece.h"
+
+// All section references below are to http://tools.ietf.org/html/rfc7541.
+
+namespace spdy {
+
+namespace test {
+class HpackHeaderTablePeer;
+}  // namespace test
+
+// A data structure for the static table (2.3.1) and the dynamic table (2.3.2).
+class SPDY_EXPORT_PRIVATE HpackHeaderTable {
+ public:
+  friend class test::HpackHeaderTablePeer;
+
+  // Debug visitor my be used to extract debug/internal information
+  // about the HpackHeaderTable as it operates.
+  //
+  // Most HpackHeaderTable implementations do not need to bother with
+  // this interface at all.
+  class DebugVisitorInterface {
+   public:
+    virtual ~DebugVisitorInterface() {}
+
+    // |OnNewEntry()| and |OnUseEntry()| can be used together to
+    // gather data about the distribution of time intervals between
+    // creation and reference of entries in the dynamic table.  The
+    // data is desired to sanity check a proposed extension to HPACK
+    // for QUIC that would eliminate inter-stream head of line
+    // blocking (due to standard HPACK).  The visitor should return
+    // the current time from |OnNewEntry()|, which will be passed
+    // to |OnUseEntry()| each time that particular entry is used to
+    // emit an indexed representation.
+    virtual int64_t OnNewEntry(const HpackEntry& entry) = 0;
+    virtual void OnUseEntry(const HpackEntry& entry) = 0;
+  };
+
+  // HpackHeaderTable takes advantage of the deque property that references
+  // remain valid, so long as insertions & deletions are at the head & tail.
+  // This precludes the use of base::circular_deque.
+  //
+  // If this changes (we want to change to circular_deque or we start to drop
+  // entries from the middle of the table), this should to be a std::list, in
+  // which case |*_index_| can be trivially extended to map to list iterators.
+  using EntryTable = std::deque<HpackEntry>;
+
+  struct SPDY_EXPORT_PRIVATE EntryHasher {
+    size_t operator()(const HpackEntry* entry) const;
+  };
+  struct SPDY_EXPORT_PRIVATE EntriesEq {
+    bool operator()(const HpackEntry* lhs, const HpackEntry* rhs) const;
+  };
+  using UnorderedEntrySet = SpdyHashSet<HpackEntry*, EntryHasher, EntriesEq>;
+  using NameToEntryMap =
+      SpdyHashMap<SpdyStringPiece, const HpackEntry*, SpdyStringPieceHash>;
+
+  HpackHeaderTable();
+  HpackHeaderTable(const HpackHeaderTable&) = delete;
+  HpackHeaderTable& operator=(const HpackHeaderTable&) = delete;
+
+  ~HpackHeaderTable();
+
+  // Last-acknowledged value of SETTINGS_HEADER_TABLE_SIZE.
+  size_t settings_size_bound() const { return settings_size_bound_; }
+
+  // Current and maximum estimated byte size of the table, as described in
+  // 4.1. Notably, this is /not/ the number of entries in the table.
+  size_t size() const { return size_; }
+  size_t max_size() const { return max_size_; }
+
+  // Returns the entry matching the index, or NULL.
+  const HpackEntry* GetByIndex(size_t index);
+
+  // Returns the lowest-value entry having |name|, or NULL.
+  const HpackEntry* GetByName(SpdyStringPiece name);
+
+  // Returns the lowest-index matching entry, or NULL.
+  const HpackEntry* GetByNameAndValue(SpdyStringPiece name,
+                                      SpdyStringPiece value);
+
+  // Returns the index of an entry within this header table.
+  size_t IndexOf(const HpackEntry* entry) const;
+
+  // Sets the maximum size of the header table, evicting entries if
+  // necessary as described in 5.2.
+  void SetMaxSize(size_t max_size);
+
+  // Sets the SETTINGS_HEADER_TABLE_SIZE bound of the table. Will call
+  // SetMaxSize() as needed to preserve max_size() <= settings_size_bound().
+  void SetSettingsHeaderTableSize(size_t settings_size);
+
+  // Determine the set of entries which would be evicted by the insertion
+  // of |name| & |value| into the table, as per section 4.4. No eviction
+  // actually occurs. The set is returned via range [begin_out, end_out).
+  void EvictionSet(SpdyStringPiece name,
+                   SpdyStringPiece value,
+                   EntryTable::iterator* begin_out,
+                   EntryTable::iterator* end_out);
+
+  // Adds an entry for the representation, evicting entries as needed. |name|
+  // and |value| must not be owned by an entry which could be evicted. The
+  // added HpackEntry is returned, or NULL is returned if all entries were
+  // evicted and the empty table is of insufficent size for the representation.
+  const HpackEntry* TryAddEntry(SpdyStringPiece name, SpdyStringPiece value);
+
+  void DebugLogTableState() const SPDY_UNUSED;
+
+  void set_debug_visitor(std::unique_ptr<DebugVisitorInterface> visitor) {
+    debug_visitor_ = std::move(visitor);
+  }
+
+  // Returns the estimate of dynamically allocated memory in bytes.
+  size_t EstimateMemoryUsage() const;
+
+ private:
+  // Returns number of evictions required to enter |name| & |value|.
+  size_t EvictionCountForEntry(SpdyStringPiece name,
+                               SpdyStringPiece value) const;
+
+  // Returns number of evictions required to reclaim |reclaim_size| table size.
+  size_t EvictionCountToReclaim(size_t reclaim_size) const;
+
+  // Evicts |count| oldest entries from the table.
+  void Evict(size_t count);
+
+  // |static_entries_|, |static_index_|, and |static_name_index_| are owned by
+  // HpackStaticTable singleton.
+
+  // Tracks HpackEntries by index.
+  const EntryTable& static_entries_;
+  EntryTable dynamic_entries_;
+
+  // Tracks the unique HpackEntry for a given header name and value.
+  const UnorderedEntrySet& static_index_;
+
+  // Tracks the first static entry for each name in the static table.
+  const NameToEntryMap& static_name_index_;
+
+  // Tracks the most recently inserted HpackEntry for a given header name and
+  // value.
+  UnorderedEntrySet dynamic_index_;
+
+  // Tracks the most recently inserted HpackEntry for a given header name.
+  NameToEntryMap dynamic_name_index_;
+
+  // Last acknowledged value for SETTINGS_HEADER_TABLE_SIZE.
+  size_t settings_size_bound_;
+
+  // Estimated current and maximum byte size of the table.
+  // |max_size_| <= |settings_size_bound_|
+  size_t size_;
+  size_t max_size_;
+
+  // Total number of table insertions which have occurred. Referenced by
+  // IndexOf() for determination of an HpackEntry's table index.
+  size_t total_insertions_;
+
+  std::unique_ptr<DebugVisitorInterface> debug_visitor_;
+};
+
+}  // namespace spdy
+
+#endif  // QUICHE_SPDY_CORE_HPACK_HPACK_HEADER_TABLE_H_
diff --git a/spdy/core/hpack/hpack_header_table_test.cc b/spdy/core/hpack/hpack_header_table_test.cc
new file mode 100644
index 0000000..b032aba
--- /dev/null
+++ b/spdy/core/hpack/hpack_header_table_test.cc
@@ -0,0 +1,446 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_header_table.h"
+
+#include <algorithm>
+#include <cstdint>
+#include <set>
+#include <vector>
+
+#include "base/macros.h"
+#include "testing/gtest/include/gtest/gtest.h"
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_constants.h"
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_entry.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string.h"
+
+namespace spdy {
+
+using std::distance;
+
+namespace test {
+
+class HpackHeaderTablePeer {
+ public:
+  explicit HpackHeaderTablePeer(HpackHeaderTable* table) : table_(table) {}
+
+  const HpackHeaderTable::EntryTable& dynamic_entries() {
+    return table_->dynamic_entries_;
+  }
+  const HpackHeaderTable::EntryTable& static_entries() {
+    return table_->static_entries_;
+  }
+  size_t index_size() {
+    return table_->static_index_.size() + table_->dynamic_index_.size();
+  }
+  std::vector<HpackEntry*> EvictionSet(SpdyStringPiece name,
+                                       SpdyStringPiece value) {
+    HpackHeaderTable::EntryTable::iterator begin, end;
+    table_->EvictionSet(name, value, &begin, &end);
+    std::vector<HpackEntry*> result;
+    for (; begin != end; ++begin) {
+      result.push_back(&(*begin));
+    }
+    return result;
+  }
+  size_t total_insertions() { return table_->total_insertions_; }
+  size_t dynamic_entries_count() { return table_->dynamic_entries_.size(); }
+  size_t EvictionCountForEntry(SpdyStringPiece name, SpdyStringPiece value) {
+    return table_->EvictionCountForEntry(name, value);
+  }
+  size_t EvictionCountToReclaim(size_t reclaim_size) {
+    return table_->EvictionCountToReclaim(reclaim_size);
+  }
+  void Evict(size_t count) { return table_->Evict(count); }
+
+  void AddDynamicEntry(SpdyStringPiece name, SpdyStringPiece value) {
+    table_->dynamic_entries_.push_back(
+        HpackEntry(name, value, false, table_->total_insertions_++));
+  }
+
+ private:
+  HpackHeaderTable* table_;
+};
+
+}  // namespace test
+
+namespace {
+
+class HpackHeaderTableTest : public ::testing::Test {
+ protected:
+  typedef std::vector<HpackEntry> HpackEntryVector;
+
+  HpackHeaderTableTest() : table_(), peer_(&table_) {}
+
+  // Returns an entry whose Size() is equal to the given one.
+  static HpackEntry MakeEntryOfSize(uint32_t size) {
+    EXPECT_GE(size, HpackEntry::kSizeOverhead);
+    SpdyString name((size - HpackEntry::kSizeOverhead) / 2, 'n');
+    SpdyString value(size - HpackEntry::kSizeOverhead - name.size(), 'v');
+    HpackEntry entry(name, value, false, 0);
+    EXPECT_EQ(size, entry.Size());
+    return entry;
+  }
+
+  // Returns a vector of entries whose total size is equal to the given
+  // one.
+  static HpackEntryVector MakeEntriesOfTotalSize(uint32_t total_size) {
+    EXPECT_GE(total_size, HpackEntry::kSizeOverhead);
+    uint32_t entry_size = HpackEntry::kSizeOverhead;
+    uint32_t remaining_size = total_size;
+    HpackEntryVector entries;
+    while (remaining_size > 0) {
+      EXPECT_LE(entry_size, remaining_size);
+      entries.push_back(MakeEntryOfSize(entry_size));
+      remaining_size -= entry_size;
+      entry_size = std::min(remaining_size, entry_size + 32);
+    }
+    return entries;
+  }
+
+  // Adds the given vector of entries to the given header table,
+  // expecting no eviction to happen.
+  void AddEntriesExpectNoEviction(const HpackEntryVector& entries) {
+    for (auto it = entries.begin(); it != entries.end(); ++it) {
+      HpackHeaderTable::EntryTable::iterator begin, end;
+
+      table_.EvictionSet(it->name(), it->value(), &begin, &end);
+      EXPECT_EQ(0, distance(begin, end));
+
+      const HpackEntry* entry = table_.TryAddEntry(it->name(), it->value());
+      EXPECT_NE(entry, static_cast<HpackEntry*>(nullptr));
+    }
+
+    for (size_t i = 0; i != entries.size(); ++i) {
+      // Static table has 61 entries, dynamic entries follow those.
+      size_t index = 61 + entries.size() - i;
+      const HpackEntry* entry = table_.GetByIndex(index);
+      EXPECT_EQ(entries[i].name(), entry->name());
+      EXPECT_EQ(entries[i].value(), entry->value());
+      EXPECT_EQ(index, table_.IndexOf(entry));
+    }
+  }
+
+  HpackEntry DynamicEntry(const SpdyString& name, const SpdyString& value) {
+    peer_.AddDynamicEntry(name, value);
+    return peer_.dynamic_entries().back();
+  }
+
+  HpackHeaderTable table_;
+  test::HpackHeaderTablePeer peer_;
+};
+
+TEST_F(HpackHeaderTableTest, StaticTableInitialization) {
+  EXPECT_EQ(0u, table_.size());
+  EXPECT_EQ(kDefaultHeaderTableSizeSetting, table_.max_size());
+  EXPECT_EQ(kDefaultHeaderTableSizeSetting, table_.settings_size_bound());
+
+  EXPECT_EQ(0u, peer_.dynamic_entries_count());
+  EXPECT_EQ(peer_.static_entries().size(), peer_.total_insertions());
+
+  // Static entries have been populated and inserted into the table & index.
+  EXPECT_NE(0u, peer_.static_entries().size());
+  EXPECT_EQ(peer_.index_size(), peer_.static_entries().size());
+  for (size_t i = 0; i != peer_.static_entries().size(); ++i) {
+    const HpackEntry* entry = &peer_.static_entries()[i];
+
+    EXPECT_TRUE(entry->IsStatic());
+    EXPECT_EQ(entry, table_.GetByIndex(i + 1));
+    EXPECT_EQ(entry, table_.GetByNameAndValue(entry->name(), entry->value()));
+  }
+}
+
+TEST_F(HpackHeaderTableTest, BasicDynamicEntryInsertionAndEviction) {
+  size_t static_count = peer_.total_insertions();
+  const HpackEntry* first_static_entry = table_.GetByIndex(1);
+
+  EXPECT_EQ(1u, table_.IndexOf(first_static_entry));
+
+  const HpackEntry* entry = table_.TryAddEntry("header-key", "Header Value");
+  EXPECT_EQ("header-key", entry->name());
+  EXPECT_EQ("Header Value", entry->value());
+  EXPECT_FALSE(entry->IsStatic());
+
+  // Table counts were updated appropriately.
+  EXPECT_EQ(entry->Size(), table_.size());
+  EXPECT_EQ(1u, peer_.dynamic_entries_count());
+  EXPECT_EQ(peer_.dynamic_entries().size(), peer_.dynamic_entries_count());
+  EXPECT_EQ(static_count + 1, peer_.total_insertions());
+  EXPECT_EQ(static_count + 1, peer_.index_size());
+
+  // Index() of entries reflects the insertion.
+  EXPECT_EQ(1u, table_.IndexOf(first_static_entry));
+  // Static table has 61 entries.
+  EXPECT_EQ(62u, table_.IndexOf(entry));
+  EXPECT_EQ(first_static_entry, table_.GetByIndex(1));
+  EXPECT_EQ(entry, table_.GetByIndex(62));
+
+  // Evict |entry|. Table counts are again updated appropriately.
+  peer_.Evict(1);
+  EXPECT_EQ(0u, table_.size());
+  EXPECT_EQ(0u, peer_.dynamic_entries_count());
+  EXPECT_EQ(peer_.dynamic_entries().size(), peer_.dynamic_entries_count());
+  EXPECT_EQ(static_count + 1, peer_.total_insertions());
+  EXPECT_EQ(static_count, peer_.index_size());
+
+  // Index() of |first_static_entry| reflects the eviction.
+  EXPECT_EQ(1u, table_.IndexOf(first_static_entry));
+  EXPECT_EQ(first_static_entry, table_.GetByIndex(1));
+}
+
+TEST_F(HpackHeaderTableTest, EntryIndexing) {
+  const HpackEntry* first_static_entry = table_.GetByIndex(1);
+
+  // Static entries are queryable by name & value.
+  EXPECT_EQ(first_static_entry, table_.GetByName(first_static_entry->name()));
+  EXPECT_EQ(first_static_entry,
+            table_.GetByNameAndValue(first_static_entry->name(),
+                                     first_static_entry->value()));
+
+  // Create a mix of entries which duplicate names, and names & values of both
+  // dynamic and static entries.
+  const HpackEntry* entry1 = table_.TryAddEntry(first_static_entry->name(),
+                                                first_static_entry->value());
+  const HpackEntry* entry2 =
+      table_.TryAddEntry(first_static_entry->name(), "Value Four");
+  const HpackEntry* entry3 = table_.TryAddEntry("key-1", "Value One");
+  const HpackEntry* entry4 = table_.TryAddEntry("key-2", "Value Three");
+  const HpackEntry* entry5 = table_.TryAddEntry("key-1", "Value Two");
+  const HpackEntry* entry6 = table_.TryAddEntry("key-2", "Value Three");
+  const HpackEntry* entry7 = table_.TryAddEntry("key-2", "Value Four");
+
+  // Entries are queryable under their current index.
+  EXPECT_EQ(entry7, table_.GetByIndex(62));
+  EXPECT_EQ(entry6, table_.GetByIndex(63));
+  EXPECT_EQ(entry5, table_.GetByIndex(64));
+  EXPECT_EQ(entry4, table_.GetByIndex(65));
+  EXPECT_EQ(entry3, table_.GetByIndex(66));
+  EXPECT_EQ(entry2, table_.GetByIndex(67));
+  EXPECT_EQ(entry1, table_.GetByIndex(68));
+  EXPECT_EQ(first_static_entry, table_.GetByIndex(1));
+
+  // Querying by name returns the most recently added matching entry.
+  EXPECT_EQ(entry5, table_.GetByName("key-1"));
+  EXPECT_EQ(entry7, table_.GetByName("key-2"));
+  EXPECT_EQ(entry2->name(),
+            table_.GetByName(first_static_entry->name())->name());
+  EXPECT_EQ(nullptr, table_.GetByName("not-present"));
+
+  // Querying by name & value returns the lowest-index matching entry among
+  // static entries, and the highest-index one among dynamic entries.
+  EXPECT_EQ(entry3, table_.GetByNameAndValue("key-1", "Value One"));
+  EXPECT_EQ(entry5, table_.GetByNameAndValue("key-1", "Value Two"));
+  EXPECT_EQ(entry6, table_.GetByNameAndValue("key-2", "Value Three"));
+  EXPECT_EQ(entry7, table_.GetByNameAndValue("key-2", "Value Four"));
+  EXPECT_EQ(first_static_entry,
+            table_.GetByNameAndValue(first_static_entry->name(),
+                                     first_static_entry->value()));
+  EXPECT_EQ(entry2,
+            table_.GetByNameAndValue(first_static_entry->name(), "Value Four"));
+  EXPECT_EQ(nullptr, table_.GetByNameAndValue("key-1", "Not Present"));
+  EXPECT_EQ(nullptr, table_.GetByNameAndValue("not-present", "Value One"));
+
+  // Evict |entry1|. Queries for its name & value now return the static entry.
+  // |entry2| remains queryable.
+  peer_.Evict(1);
+  EXPECT_EQ(first_static_entry,
+            table_.GetByNameAndValue(first_static_entry->name(),
+                                     first_static_entry->value()));
+  EXPECT_EQ(entry2,
+            table_.GetByNameAndValue(first_static_entry->name(), "Value Four"));
+
+  // Evict |entry2|. Queries by its name & value are not found.
+  peer_.Evict(1);
+  EXPECT_EQ(nullptr,
+            table_.GetByNameAndValue(first_static_entry->name(), "Value Four"));
+}
+
+TEST_F(HpackHeaderTableTest, SetSizes) {
+  SpdyString key = "key", value = "value";
+  const HpackEntry* entry1 = table_.TryAddEntry(key, value);
+  const HpackEntry* entry2 = table_.TryAddEntry(key, value);
+  const HpackEntry* entry3 = table_.TryAddEntry(key, value);
+
+  // Set exactly large enough. No Evictions.
+  size_t max_size = entry1->Size() + entry2->Size() + entry3->Size();
+  table_.SetMaxSize(max_size);
+  EXPECT_EQ(3u, peer_.dynamic_entries().size());
+
+  // Set just too small. One eviction.
+  max_size = entry1->Size() + entry2->Size() + entry3->Size() - 1;
+  table_.SetMaxSize(max_size);
+  EXPECT_EQ(2u, peer_.dynamic_entries().size());
+
+  // Changing SETTINGS_HEADER_TABLE_SIZE.
+  EXPECT_EQ(kDefaultHeaderTableSizeSetting, table_.settings_size_bound());
+  // In production, the size passed to SetSettingsHeaderTableSize is never
+  // larger than table_.settings_size_bound().
+  table_.SetSettingsHeaderTableSize(kDefaultHeaderTableSizeSetting * 3 + 1);
+  EXPECT_EQ(kDefaultHeaderTableSizeSetting * 3 + 1, table_.max_size());
+
+  // SETTINGS_HEADER_TABLE_SIZE upper-bounds |table_.max_size()|,
+  // and will force evictions.
+  max_size = entry3->Size() - 1;
+  table_.SetSettingsHeaderTableSize(max_size);
+  EXPECT_EQ(max_size, table_.max_size());
+  EXPECT_EQ(max_size, table_.settings_size_bound());
+  EXPECT_EQ(0u, peer_.dynamic_entries().size());
+}
+
+TEST_F(HpackHeaderTableTest, EvictionCountForEntry) {
+  SpdyString key = "key", value = "value";
+  const HpackEntry* entry1 = table_.TryAddEntry(key, value);
+  const HpackEntry* entry2 = table_.TryAddEntry(key, value);
+  size_t entry3_size = HpackEntry::Size(key, value);
+
+  // Just enough capacity for third entry.
+  table_.SetMaxSize(entry1->Size() + entry2->Size() + entry3_size);
+  EXPECT_EQ(0u, peer_.EvictionCountForEntry(key, value));
+  EXPECT_EQ(1u, peer_.EvictionCountForEntry(key, value + "x"));
+
+  // No extra capacity. Third entry would force evictions.
+  table_.SetMaxSize(entry1->Size() + entry2->Size());
+  EXPECT_EQ(1u, peer_.EvictionCountForEntry(key, value));
+  EXPECT_EQ(2u, peer_.EvictionCountForEntry(key, value + "x"));
+}
+
+TEST_F(HpackHeaderTableTest, EvictionCountToReclaim) {
+  SpdyString key = "key", value = "value";
+  const HpackEntry* entry1 = table_.TryAddEntry(key, value);
+  const HpackEntry* entry2 = table_.TryAddEntry(key, value);
+
+  EXPECT_EQ(1u, peer_.EvictionCountToReclaim(1));
+  EXPECT_EQ(1u, peer_.EvictionCountToReclaim(entry1->Size()));
+  EXPECT_EQ(2u, peer_.EvictionCountToReclaim(entry1->Size() + 1));
+  EXPECT_EQ(2u, peer_.EvictionCountToReclaim(entry1->Size() + entry2->Size()));
+}
+
+// Fill a header table with entries. Make sure the entries are in
+// reverse order in the header table.
+TEST_F(HpackHeaderTableTest, TryAddEntryBasic) {
+  EXPECT_EQ(0u, table_.size());
+  EXPECT_EQ(table_.settings_size_bound(), table_.max_size());
+
+  HpackEntryVector entries = MakeEntriesOfTotalSize(table_.max_size());
+
+  // Most of the checks are in AddEntriesExpectNoEviction().
+  AddEntriesExpectNoEviction(entries);
+  EXPECT_EQ(table_.max_size(), table_.size());
+  EXPECT_EQ(table_.settings_size_bound(), table_.size());
+}
+
+// Fill a header table with entries, and then ramp the table's max
+// size down to evict an entry one at a time. Make sure the eviction
+// happens as expected.
+TEST_F(HpackHeaderTableTest, SetMaxSize) {
+  HpackEntryVector entries =
+      MakeEntriesOfTotalSize(kDefaultHeaderTableSizeSetting / 2);
+  AddEntriesExpectNoEviction(entries);
+
+  for (auto it = entries.begin(); it != entries.end(); ++it) {
+    size_t expected_count = distance(it, entries.end());
+    EXPECT_EQ(expected_count, peer_.dynamic_entries().size());
+
+    table_.SetMaxSize(table_.size() + 1);
+    EXPECT_EQ(expected_count, peer_.dynamic_entries().size());
+
+    table_.SetMaxSize(table_.size());
+    EXPECT_EQ(expected_count, peer_.dynamic_entries().size());
+
+    --expected_count;
+    table_.SetMaxSize(table_.size() - 1);
+    EXPECT_EQ(expected_count, peer_.dynamic_entries().size());
+  }
+  EXPECT_EQ(0u, table_.size());
+}
+
+// Fill a header table with entries, and then add an entry just big
+// enough to cause eviction of all but one entry. Make sure the
+// eviction happens as expected and the long entry is inserted into
+// the table.
+TEST_F(HpackHeaderTableTest, TryAddEntryEviction) {
+  HpackEntryVector entries = MakeEntriesOfTotalSize(table_.max_size());
+  AddEntriesExpectNoEviction(entries);
+
+  const HpackEntry* survivor_entry = table_.GetByIndex(61 + 1);
+  HpackEntry long_entry =
+      MakeEntryOfSize(table_.max_size() - survivor_entry->Size());
+
+  // All dynamic entries but the first are to be evicted.
+  EXPECT_EQ(peer_.dynamic_entries().size() - 1,
+            peer_.EvictionSet(long_entry.name(), long_entry.value()).size());
+
+  const HpackEntry* new_entry =
+      table_.TryAddEntry(long_entry.name(), long_entry.value());
+  EXPECT_EQ(62u, table_.IndexOf(new_entry));
+  EXPECT_EQ(2u, peer_.dynamic_entries().size());
+  EXPECT_EQ(table_.GetByIndex(63), survivor_entry);
+  EXPECT_EQ(table_.GetByIndex(62), new_entry);
+}
+
+// Fill a header table with entries, and then add an entry bigger than
+// the entire table. Make sure no entry remains in the table.
+TEST_F(HpackHeaderTableTest, TryAddTooLargeEntry) {
+  HpackEntryVector entries = MakeEntriesOfTotalSize(table_.max_size());
+  AddEntriesExpectNoEviction(entries);
+
+  const HpackEntry long_entry = MakeEntryOfSize(table_.max_size() + 1);
+
+  // All entries are to be evicted.
+  EXPECT_EQ(peer_.dynamic_entries().size(),
+            peer_.EvictionSet(long_entry.name(), long_entry.value()).size());
+
+  const HpackEntry* new_entry =
+      table_.TryAddEntry(long_entry.name(), long_entry.value());
+  EXPECT_EQ(new_entry, static_cast<HpackEntry*>(nullptr));
+  EXPECT_EQ(0u, peer_.dynamic_entries().size());
+}
+
+TEST_F(HpackHeaderTableTest, EntryNamesDiffer) {
+  HpackEntry entry1("header", "value");
+  HpackEntry entry2("HEADER", "value");
+
+  HpackHeaderTable::EntryHasher hasher;
+  EXPECT_NE(hasher(&entry1), hasher(&entry2));
+
+  HpackHeaderTable::EntriesEq eq;
+  EXPECT_FALSE(eq(&entry1, &entry2));
+}
+
+TEST_F(HpackHeaderTableTest, EntryValuesDiffer) {
+  HpackEntry entry1("header", "value");
+  HpackEntry entry2("header", "VALUE");
+
+  HpackHeaderTable::EntryHasher hasher;
+  EXPECT_NE(hasher(&entry1), hasher(&entry2));
+
+  HpackHeaderTable::EntriesEq eq;
+  EXPECT_FALSE(eq(&entry1, &entry2));
+}
+
+TEST_F(HpackHeaderTableTest, EntriesEqual) {
+  HpackEntry entry1(DynamicEntry("name", "value"));
+  HpackEntry entry2(DynamicEntry("name", "value"));
+
+  HpackHeaderTable::EntryHasher hasher;
+  EXPECT_EQ(hasher(&entry1), hasher(&entry2));
+
+  HpackHeaderTable::EntriesEq eq;
+  EXPECT_TRUE(eq(&entry1, &entry2));
+}
+
+TEST_F(HpackHeaderTableTest, StaticAndDynamicEntriesEqual) {
+  HpackEntry entry1("name", "value");
+  HpackEntry entry2(DynamicEntry("name", "value"));
+
+  HpackHeaderTable::EntryHasher hasher;
+  EXPECT_EQ(hasher(&entry1), hasher(&entry2));
+
+  HpackHeaderTable::EntriesEq eq;
+  EXPECT_TRUE(eq(&entry1, &entry2));
+}
+
+}  // namespace
+
+}  // namespace spdy
diff --git a/spdy/core/hpack/hpack_huffman_table.cc b/spdy/core/hpack/hpack_huffman_table.cc
new file mode 100644
index 0000000..c917767
--- /dev/null
+++ b/spdy/core/hpack/hpack_huffman_table.cc
@@ -0,0 +1,151 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_huffman_table.h"
+
+#include <algorithm>
+#include <cmath>
+#include <limits>
+#include <memory>
+
+#include "base/logging.h"
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_output_stream.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_estimate_memory_usage.h"
+
+namespace spdy {
+
+namespace {
+
+bool SymbolLengthAndIdCompare(const HpackHuffmanSymbol& a,
+                              const HpackHuffmanSymbol& b) {
+  if (a.length == b.length) {
+    return a.id < b.id;
+  }
+  return a.length < b.length;
+}
+bool SymbolIdCompare(const HpackHuffmanSymbol& a, const HpackHuffmanSymbol& b) {
+  return a.id < b.id;
+}
+
+}  // namespace
+
+HpackHuffmanTable::HpackHuffmanTable() : pad_bits_(0), failed_symbol_id_(0) {}
+
+HpackHuffmanTable::~HpackHuffmanTable() = default;
+
+bool HpackHuffmanTable::Initialize(const HpackHuffmanSymbol* input_symbols,
+                                   size_t symbol_count) {
+  CHECK(!IsInitialized());
+  DCHECK_LE(symbol_count, std::numeric_limits<uint16_t>::max());
+
+  std::vector<Symbol> symbols(symbol_count);
+  // Validate symbol id sequence, and copy into |symbols|.
+  for (uint16_t i = 0; i < symbol_count; i++) {
+    if (i != input_symbols[i].id) {
+      failed_symbol_id_ = i;
+      return false;
+    }
+    symbols[i] = input_symbols[i];
+  }
+  // Order on length and ID ascending, to verify symbol codes are canonical.
+  std::sort(symbols.begin(), symbols.end(), SymbolLengthAndIdCompare);
+  if (symbols[0].code != 0) {
+    failed_symbol_id_ = 0;
+    return false;
+  }
+  for (size_t i = 1; i != symbols.size(); i++) {
+    unsigned code_shift = 32 - symbols[i - 1].length;
+    uint32_t code = symbols[i - 1].code + (1 << code_shift);
+
+    if (code != symbols[i].code) {
+      failed_symbol_id_ = symbols[i].id;
+      return false;
+    }
+    if (code < symbols[i - 1].code) {
+      // An integer overflow occurred. This implies the input
+      // lengths do not represent a valid Huffman code.
+      failed_symbol_id_ = symbols[i].id;
+      return false;
+    }
+  }
+  if (symbols.back().length < 8) {
+    // At least one code (such as an EOS symbol) must be 8 bits or longer.
+    // Without this, some inputs will not be encodable in a whole number
+    // of bytes.
+    return false;
+  }
+  pad_bits_ = static_cast<uint8_t>(symbols.back().code >> 24);
+
+  // Order on symbol ID ascending.
+  std::sort(symbols.begin(), symbols.end(), SymbolIdCompare);
+  BuildEncodeTable(symbols);
+  return true;
+}
+
+void HpackHuffmanTable::BuildEncodeTable(const std::vector<Symbol>& symbols) {
+  for (size_t i = 0; i != symbols.size(); i++) {
+    const Symbol& symbol = symbols[i];
+    CHECK_EQ(i, symbol.id);
+    code_by_id_.push_back(symbol.code);
+    length_by_id_.push_back(symbol.length);
+  }
+}
+
+bool HpackHuffmanTable::IsInitialized() const {
+  return !code_by_id_.empty();
+}
+
+void HpackHuffmanTable::EncodeString(SpdyStringPiece in,
+                                     HpackOutputStream* out) const {
+  size_t bit_remnant = 0;
+  for (size_t i = 0; i != in.size(); i++) {
+    uint16_t symbol_id = static_cast<uint8_t>(in[i]);
+    CHECK_GT(code_by_id_.size(), symbol_id);
+
+    // Load, and shift code to low bits.
+    unsigned length = length_by_id_[symbol_id];
+    uint32_t code = code_by_id_[symbol_id] >> (32 - length);
+
+    bit_remnant = (bit_remnant + length) % 8;
+
+    if (length > 24) {
+      out->AppendBits(static_cast<uint8_t>(code >> 24), length - 24);
+      length = 24;
+    }
+    if (length > 16) {
+      out->AppendBits(static_cast<uint8_t>(code >> 16), length - 16);
+      length = 16;
+    }
+    if (length > 8) {
+      out->AppendBits(static_cast<uint8_t>(code >> 8), length - 8);
+      length = 8;
+    }
+    out->AppendBits(static_cast<uint8_t>(code), length);
+  }
+  if (bit_remnant != 0) {
+    // Pad current byte as required.
+    out->AppendBits(pad_bits_ >> bit_remnant, 8 - bit_remnant);
+  }
+}
+
+size_t HpackHuffmanTable::EncodedSize(SpdyStringPiece in) const {
+  size_t bit_count = 0;
+  for (size_t i = 0; i != in.size(); i++) {
+    uint16_t symbol_id = static_cast<uint8_t>(in[i]);
+    CHECK_GT(code_by_id_.size(), symbol_id);
+
+    bit_count += length_by_id_[symbol_id];
+  }
+  if (bit_count % 8 != 0) {
+    bit_count += 8 - bit_count % 8;
+  }
+  return bit_count / 8;
+}
+
+size_t HpackHuffmanTable::EstimateMemoryUsage() const {
+  return SpdyEstimateMemoryUsage(code_by_id_) +
+         SpdyEstimateMemoryUsage(length_by_id_);
+}
+
+}  // namespace spdy
diff --git a/spdy/core/hpack/hpack_huffman_table.h b/spdy/core/hpack/hpack_huffman_table.h
new file mode 100644
index 0000000..80d9e52
--- /dev/null
+++ b/spdy/core/hpack/hpack_huffman_table.h
@@ -0,0 +1,76 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef QUICHE_SPDY_CORE_HPACK_HPACK_HUFFMAN_TABLE_H_
+#define QUICHE_SPDY_CORE_HPACK_HPACK_HUFFMAN_TABLE_H_
+
+#include <cstddef>
+#include <cstdint>
+#include <vector>
+
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_constants.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_export.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string_piece.h"
+
+namespace spdy {
+
+namespace test {
+class HpackHuffmanTablePeer;
+}  // namespace test
+
+class HpackOutputStream;
+
+// HpackHuffmanTable encodes string literals using a constructed canonical
+// Huffman code. Once initialized, an instance is read only and may be accessed
+// only through its const interface.
+class SPDY_EXPORT_PRIVATE HpackHuffmanTable {
+ public:
+  friend class test::HpackHuffmanTablePeer;
+
+  typedef HpackHuffmanSymbol Symbol;
+
+  HpackHuffmanTable();
+  ~HpackHuffmanTable();
+
+  // Prepares HpackHuffmanTable to encode the canonical Huffman code as
+  // determined by the given symbols. Must be called exactly once.
+  // Returns false if the input symbols define an invalid coding, and true
+  // otherwise. Symbols must be presented in ascending ID order with no gaps,
+  // and |symbol_count| must fit in a uint16_t.
+  bool Initialize(const Symbol* input_symbols, size_t symbol_count);
+
+  // Returns whether Initialize() has been successfully called.
+  bool IsInitialized() const;
+
+  // Encodes the input string to the output stream using the table's Huffman
+  // context.
+  void EncodeString(SpdyStringPiece in, HpackOutputStream* out) const;
+
+  // Returns the encoded size of the input string.
+  size_t EncodedSize(SpdyStringPiece in) const;
+
+  // Returns the estimate of dynamically allocated memory in bytes.
+  size_t EstimateMemoryUsage() const;
+
+ private:
+  // Expects symbols ordered on ID ascending.
+  void BuildEncodeTable(const std::vector<Symbol>& symbols);
+
+  // Symbol code and code length, in ascending symbol ID order.
+  // Codes are stored in the most-significant bits of the word.
+  std::vector<uint32_t> code_by_id_;
+  std::vector<uint8_t> length_by_id_;
+
+  // The first 8 bits of the longest code. Applied when generating padding bits.
+  uint8_t pad_bits_;
+
+  // If initialization fails, preserve the symbol ID which failed validation
+  // for examination in tests.
+  uint16_t failed_symbol_id_;
+};
+
+}  // namespace spdy
+
+#endif  // QUICHE_SPDY_CORE_HPACK_HPACK_HUFFMAN_TABLE_H_
diff --git a/spdy/core/hpack/hpack_huffman_table_test.cc b/spdy/core/hpack/hpack_huffman_table_test.cc
new file mode 100644
index 0000000..f30926c
--- /dev/null
+++ b/spdy/core/hpack/hpack_huffman_table_test.cc
@@ -0,0 +1,309 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_huffman_table.h"
+
+#include <utility>
+
+#include "base/macros.h"
+#include "testing/gmock/include/gmock/gmock.h"
+#include "testing/gtest/include/gtest/gtest.h"
+#include "net/third_party/quiche/src/http2/hpack/huffman/hpack_huffman_decoder.h"
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_constants.h"
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_output_stream.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_arraysize.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string_utils.h"
+
+namespace spdy {
+
+namespace test {
+
+class HpackHuffmanTablePeer {
+ public:
+  explicit HpackHuffmanTablePeer(const HpackHuffmanTable& table)
+      : table_(table) {}
+
+  const std::vector<uint32_t>& code_by_id() const { return table_.code_by_id_; }
+  const std::vector<uint8_t>& length_by_id() const {
+    return table_.length_by_id_;
+  }
+  uint8_t pad_bits() const { return table_.pad_bits_; }
+  uint16_t failed_symbol_id() const { return table_.failed_symbol_id_; }
+
+ private:
+  const HpackHuffmanTable& table_;
+};
+
+namespace {
+
+// Tests of the ability to encode some canonical Huffman code,
+// not just the one defined in the RFC 7541.
+class GenericHuffmanTableTest : public ::testing::Test {
+ protected:
+  GenericHuffmanTableTest() : table_(), peer_(table_) {}
+
+  SpdyString EncodeString(SpdyStringPiece input) {
+    SpdyString result;
+    HpackOutputStream output_stream;
+    table_.EncodeString(input, &output_stream);
+
+    output_stream.TakeString(&result);
+    // Verify EncodedSize() agrees with EncodeString().
+    EXPECT_EQ(result.size(), table_.EncodedSize(input));
+    return result;
+  }
+
+  HpackHuffmanTable table_;
+  HpackHuffmanTablePeer peer_;
+};
+
+TEST_F(GenericHuffmanTableTest, InitializeEdgeCases) {
+  {
+    // Verify eight symbols can be encoded with 3 bits per symbol.
+    HpackHuffmanSymbol code[] = {{0b00000000000000000000000000000000, 3, 0},
+                                 {0b00100000000000000000000000000000, 3, 1},
+                                 {0b01000000000000000000000000000000, 3, 2},
+                                 {0b01100000000000000000000000000000, 3, 3},
+                                 {0b10000000000000000000000000000000, 3, 4},
+                                 {0b10100000000000000000000000000000, 3, 5},
+                                 {0b11000000000000000000000000000000, 3, 6},
+                                 {0b11100000000000000000000000000000, 8, 7}};
+    HpackHuffmanTable table;
+    EXPECT_TRUE(table.Initialize(code, SPDY_ARRAYSIZE(code)));
+  }
+  {
+    // But using 2 bits with one symbol overflows the code.
+    HpackHuffmanSymbol code[] = {
+        {0b01000000000000000000000000000000, 3, 0},
+        {0b01100000000000000000000000000000, 3, 1},
+        {0b00000000000000000000000000000000, 2, 2},
+        {0b10000000000000000000000000000000, 3, 3},
+        {0b10100000000000000000000000000000, 3, 4},
+        {0b11000000000000000000000000000000, 3, 5},
+        {0b11100000000000000000000000000000, 3, 6},
+        {0b00000000000000000000000000000000, 8, 7}};  // Overflow.
+    HpackHuffmanTable table;
+    EXPECT_FALSE(table.Initialize(code, SPDY_ARRAYSIZE(code)));
+    EXPECT_EQ(7, HpackHuffmanTablePeer(table).failed_symbol_id());
+  }
+  {
+    // Verify four symbols can be encoded with incremental bits per symbol.
+    HpackHuffmanSymbol code[] = {{0b00000000000000000000000000000000, 1, 0},
+                                 {0b10000000000000000000000000000000, 2, 1},
+                                 {0b11000000000000000000000000000000, 3, 2},
+                                 {0b11100000000000000000000000000000, 8, 3}};
+    HpackHuffmanTable table;
+    EXPECT_TRUE(table.Initialize(code, SPDY_ARRAYSIZE(code)));
+  }
+  {
+    // But repeating a length overflows the code.
+    HpackHuffmanSymbol code[] = {
+        {0b00000000000000000000000000000000, 1, 0},
+        {0b10000000000000000000000000000000, 2, 1},
+        {0b11000000000000000000000000000000, 2, 2},
+        {0b00000000000000000000000000000000, 8, 3}};  // Overflow.
+    HpackHuffmanTable table;
+    EXPECT_FALSE(table.Initialize(code, SPDY_ARRAYSIZE(code)));
+    EXPECT_EQ(3, HpackHuffmanTablePeer(table).failed_symbol_id());
+  }
+  {
+    // Symbol IDs must be assigned sequentially with no gaps.
+    HpackHuffmanSymbol code[] = {
+        {0b00000000000000000000000000000000, 1, 0},
+        {0b10000000000000000000000000000000, 2, 1},
+        {0b11000000000000000000000000000000, 3, 1},  // Repeat.
+        {0b11100000000000000000000000000000, 8, 3}};
+    HpackHuffmanTable table;
+    EXPECT_FALSE(table.Initialize(code, SPDY_ARRAYSIZE(code)));
+    EXPECT_EQ(2, HpackHuffmanTablePeer(table).failed_symbol_id());
+  }
+  {
+    // Canonical codes must begin with zero.
+    HpackHuffmanSymbol code[] = {{0b10000000000000000000000000000000, 4, 0},
+                                 {0b10010000000000000000000000000000, 4, 1},
+                                 {0b10100000000000000000000000000000, 4, 2},
+                                 {0b10110000000000000000000000000000, 8, 3}};
+    HpackHuffmanTable table;
+    EXPECT_FALSE(table.Initialize(code, SPDY_ARRAYSIZE(code)));
+    EXPECT_EQ(0, HpackHuffmanTablePeer(table).failed_symbol_id());
+  }
+  {
+    // Codes must match the expected canonical sequence.
+    HpackHuffmanSymbol code[] = {
+        {0b00000000000000000000000000000000, 2, 0},
+        {0b01000000000000000000000000000000, 2, 1},
+        {0b11000000000000000000000000000000, 2, 2},  // Code not canonical.
+        {0b10000000000000000000000000000000, 8, 3}};
+    HpackHuffmanTable table;
+    EXPECT_FALSE(table.Initialize(code, SPDY_ARRAYSIZE(code)));
+    EXPECT_EQ(2, HpackHuffmanTablePeer(table).failed_symbol_id());
+  }
+  {
+    // At least one code must have a length of 8 bits (to ensure pad-ability).
+    HpackHuffmanSymbol code[] = {{0b00000000000000000000000000000000, 1, 0},
+                                 {0b10000000000000000000000000000000, 2, 1},
+                                 {0b11000000000000000000000000000000, 3, 2},
+                                 {0b11100000000000000000000000000000, 7, 3}};
+    HpackHuffmanTable table;
+    EXPECT_FALSE(table.Initialize(code, SPDY_ARRAYSIZE(code)));
+  }
+}
+
+TEST_F(GenericHuffmanTableTest, ValidateInternalsWithSmallCode) {
+  HpackHuffmanSymbol code[] = {
+      {0b01100000000000000000000000000000, 4, 0},   // 3rd.
+      {0b01110000000000000000000000000000, 4, 1},   // 4th.
+      {0b00000000000000000000000000000000, 2, 2},   // 1st assigned code.
+      {0b01000000000000000000000000000000, 3, 3},   // 2nd.
+      {0b10000000000000000000000000000000, 5, 4},   // 5th.
+      {0b10001000000000000000000000000000, 5, 5},   // 6th.
+      {0b10011000000000000000000000000000, 8, 6},   // 8th.
+      {0b10010000000000000000000000000000, 5, 7}};  // 7th.
+  EXPECT_TRUE(table_.Initialize(code, SPDY_ARRAYSIZE(code)));
+
+  ASSERT_EQ(SPDY_ARRAYSIZE(code), peer_.code_by_id().size());
+  ASSERT_EQ(SPDY_ARRAYSIZE(code), peer_.length_by_id().size());
+  for (size_t i = 0; i < SPDY_ARRAYSIZE(code); ++i) {
+    EXPECT_EQ(code[i].code, peer_.code_by_id()[i]);
+    EXPECT_EQ(code[i].length, peer_.length_by_id()[i]);
+  }
+
+  EXPECT_EQ(0b10011000, peer_.pad_bits());
+
+  char input_storage[] = {2, 3, 2, 7, 4};
+  SpdyStringPiece input(input_storage, SPDY_ARRAYSIZE(input_storage));
+  // By symbol: (2) 00 (3) 010 (2) 00 (7) 10010 (4) 10000 (6 as pad) 1001100.
+  char expect_storage[] = {0b00010001, 0b00101000, 0b01001100};
+  SpdyStringPiece expect(expect_storage, SPDY_ARRAYSIZE(expect_storage));
+  EXPECT_EQ(expect, EncodeString(input));
+}
+
+// Tests of the ability to encode the HPACK Huffman Code, defined in:
+//     https://httpwg.github.io/specs/rfc7541.html#huffman.code
+class HpackHuffmanTableTest : public GenericHuffmanTableTest {
+ protected:
+  void SetUp() override {
+    EXPECT_TRUE(table_.Initialize(HpackHuffmanCodeVector().data(),
+                                  HpackHuffmanCodeVector().size()));
+    EXPECT_TRUE(table_.IsInitialized());
+  }
+
+  // Use http2::HpackHuffmanDecoder for roundtrip tests.
+  void DecodeString(const SpdyString& encoded, SpdyString* out) {
+    http2::HpackHuffmanDecoder decoder;
+    out->clear();
+    EXPECT_TRUE(decoder.Decode(encoded, out));
+  }
+};
+
+TEST_F(HpackHuffmanTableTest, InitializeHpackCode) {
+  EXPECT_EQ(peer_.pad_bits(), 0b11111111);  // First 8 bits of EOS.
+}
+
+TEST_F(HpackHuffmanTableTest, SpecRequestExamples) {
+  SpdyString buffer;
+  SpdyString test_table[] = {
+      SpdyHexDecode("f1e3c2e5f23a6ba0ab90f4ff"),
+      "www.example.com",
+      SpdyHexDecode("a8eb10649cbf"),
+      "no-cache",
+      SpdyHexDecode("25a849e95ba97d7f"),
+      "custom-key",
+      SpdyHexDecode("25a849e95bb8e8b4bf"),
+      "custom-value",
+  };
+  // Round-trip each test example.
+  for (size_t i = 0; i != SPDY_ARRAYSIZE(test_table); i += 2) {
+    const SpdyString& encodedFixture(test_table[i]);
+    const SpdyString& decodedFixture(test_table[i + 1]);
+    DecodeString(encodedFixture, &buffer);
+    EXPECT_EQ(decodedFixture, buffer);
+    buffer = EncodeString(decodedFixture);
+    EXPECT_EQ(encodedFixture, buffer);
+  }
+}
+
+TEST_F(HpackHuffmanTableTest, SpecResponseExamples) {
+  SpdyString buffer;
+  SpdyString test_table[] = {
+      SpdyHexDecode("6402"),
+      "302",
+      SpdyHexDecode("aec3771a4b"),
+      "private",
+      SpdyHexDecode("d07abe941054d444a8200595040b8166"
+                    "e082a62d1bff"),
+      "Mon, 21 Oct 2013 20:13:21 GMT",
+      SpdyHexDecode("9d29ad171863c78f0b97c8e9ae82ae43"
+                    "d3"),
+      "https://www.example.com",
+      SpdyHexDecode("94e7821dd7f2e6c7b335dfdfcd5b3960"
+                    "d5af27087f3672c1ab270fb5291f9587"
+                    "316065c003ed4ee5b1063d5007"),
+      "foo=ASDJKHQKBZXOQWEOPIUAXQWEOIU; max-age=3600; version=1",
+  };
+  // Round-trip each test example.
+  for (size_t i = 0; i != SPDY_ARRAYSIZE(test_table); i += 2) {
+    const SpdyString& encodedFixture(test_table[i]);
+    const SpdyString& decodedFixture(test_table[i + 1]);
+    DecodeString(encodedFixture, &buffer);
+    EXPECT_EQ(decodedFixture, buffer);
+    buffer = EncodeString(decodedFixture);
+    EXPECT_EQ(encodedFixture, buffer);
+  }
+}
+
+TEST_F(HpackHuffmanTableTest, RoundTripIndividualSymbols) {
+  for (size_t i = 0; i != 256; i++) {
+    char c = static_cast<char>(i);
+    char storage[3] = {c, c, c};
+    SpdyStringPiece input(storage, SPDY_ARRAYSIZE(storage));
+    SpdyString buffer_in = EncodeString(input);
+    SpdyString buffer_out;
+    DecodeString(buffer_in, &buffer_out);
+    EXPECT_EQ(input, buffer_out);
+  }
+}
+
+TEST_F(HpackHuffmanTableTest, RoundTripSymbolSequence) {
+  char storage[512];
+  for (size_t i = 0; i != 256; i++) {
+    storage[i] = static_cast<char>(i);
+    storage[511 - i] = static_cast<char>(i);
+  }
+  SpdyStringPiece input(storage, SPDY_ARRAYSIZE(storage));
+  SpdyString buffer_in = EncodeString(input);
+  SpdyString buffer_out;
+  DecodeString(buffer_in, &buffer_out);
+  EXPECT_EQ(input, buffer_out);
+}
+
+TEST_F(HpackHuffmanTableTest, EncodedSizeAgreesWithEncodeString) {
+  SpdyString test_table[] = {
+      "",
+      "Mon, 21 Oct 2013 20:13:21 GMT",
+      "https://www.example.com",
+      "foo=ASDJKHQKBZXOQWEOPIUAXQWEOIU; max-age=3600; version=1",
+      SpdyString(1, '\0'),
+      SpdyString("foo\0bar", 7),
+      SpdyString(256, '\0'),
+  };
+  for (size_t i = 0; i != 256; ++i) {
+    // Expand last |test_table| entry to cover all codes.
+    test_table[SPDY_ARRAYSIZE(test_table) - 1][i] = static_cast<char>(i);
+  }
+
+  HpackOutputStream output_stream;
+  SpdyString encoding;
+  for (size_t i = 0; i != SPDY_ARRAYSIZE(test_table); ++i) {
+    table_.EncodeString(test_table[i], &output_stream);
+    output_stream.TakeString(&encoding);
+    EXPECT_EQ(encoding.size(), table_.EncodedSize(test_table[i]));
+  }
+}
+
+}  // namespace
+
+}  // namespace test
+
+}  // namespace spdy
diff --git a/spdy/core/hpack/hpack_output_stream.cc b/spdy/core/hpack/hpack_output_stream.cc
new file mode 100644
index 0000000..30b5662
--- /dev/null
+++ b/spdy/core/hpack/hpack_output_stream.cc
@@ -0,0 +1,97 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_output_stream.h"
+
+#include <utility>
+
+#include "base/logging.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_estimate_memory_usage.h"
+
+namespace spdy {
+
+HpackOutputStream::HpackOutputStream() : bit_offset_(0) {}
+
+HpackOutputStream::~HpackOutputStream() = default;
+
+void HpackOutputStream::AppendBits(uint8_t bits, size_t bit_size) {
+  DCHECK_GT(bit_size, 0u);
+  DCHECK_LE(bit_size, 8u);
+  DCHECK_EQ(bits >> bit_size, 0);
+  size_t new_bit_offset = bit_offset_ + bit_size;
+  if (bit_offset_ == 0) {
+    // Buffer ends on a byte boundary.
+    DCHECK_LE(bit_size, 8u);
+    buffer_.append(1, bits << (8 - bit_size));
+  } else if (new_bit_offset <= 8) {
+    // Buffer does not end on a byte boundary but the given bits fit
+    // in the remainder of the last byte.
+    buffer_.back() |= bits << (8 - new_bit_offset);
+  } else {
+    // Buffer does not end on a byte boundary and the given bits do
+    // not fit in the remainder of the last byte.
+    buffer_.back() |= bits >> (new_bit_offset - 8);
+    buffer_.append(1, bits << (16 - new_bit_offset));
+  }
+  bit_offset_ = new_bit_offset % 8;
+}
+
+void HpackOutputStream::AppendPrefix(HpackPrefix prefix) {
+  AppendBits(prefix.bits, prefix.bit_size);
+}
+
+void HpackOutputStream::AppendBytes(SpdyStringPiece buffer) {
+  DCHECK_EQ(bit_offset_, 0u);
+  buffer_.append(buffer.data(), buffer.size());
+}
+
+void HpackOutputStream::AppendUint32(uint32_t I) {
+  // The algorithm below is adapted from the pseudocode in 6.1.
+  size_t N = 8 - bit_offset_;
+  uint8_t max_first_byte = static_cast<uint8_t>((1 << N) - 1);
+  if (I < max_first_byte) {
+    AppendBits(static_cast<uint8_t>(I), N);
+  } else {
+    AppendBits(max_first_byte, N);
+    I -= max_first_byte;
+    while ((I & ~0x7f) != 0) {
+      buffer_.append(1, (I & 0x7f) | 0x80);
+      I >>= 7;
+    }
+    AppendBits(static_cast<uint8_t>(I), 8);
+  }
+}
+
+void HpackOutputStream::TakeString(SpdyString* output) {
+  // This must hold, since all public functions cause the buffer to
+  // end on a byte boundary.
+  DCHECK_EQ(bit_offset_, 0u);
+  buffer_.swap(*output);
+  buffer_.clear();
+  bit_offset_ = 0;
+}
+
+void HpackOutputStream::BoundedTakeString(size_t max_size, SpdyString* output) {
+  if (buffer_.size() > max_size) {
+    // Save off overflow bytes to temporary string (causes a copy).
+    SpdyString overflow(buffer_.data() + max_size, buffer_.size() - max_size);
+
+    // Resize buffer down to the given limit.
+    buffer_.resize(max_size);
+
+    // Give buffer to output string.
+    *output = std::move(buffer_);
+
+    // Reset to contain overflow.
+    buffer_ = std::move(overflow);
+  } else {
+    TakeString(output);
+  }
+}
+
+size_t HpackOutputStream::EstimateMemoryUsage() const {
+  return SpdyEstimateMemoryUsage(buffer_);
+}
+
+}  // namespace spdy
diff --git a/spdy/core/hpack/hpack_output_stream.h b/spdy/core/hpack/hpack_output_stream.h
new file mode 100644
index 0000000..450803f
--- /dev/null
+++ b/spdy/core/hpack/hpack_output_stream.h
@@ -0,0 +1,76 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef QUICHE_SPDY_CORE_HPACK_HPACK_OUTPUT_STREAM_H_
+#define QUICHE_SPDY_CORE_HPACK_HPACK_OUTPUT_STREAM_H_
+
+#include <cstdint>
+#include <map>
+
+#include "base/macros.h"
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_constants.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_export.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string_piece.h"
+
+// All section references below are to
+// http://tools.ietf.org/html/draft-ietf-httpbis-header-compression-08
+
+namespace spdy {
+
+// An HpackOutputStream handles all the low-level details of encoding
+// header fields.
+class SPDY_EXPORT_PRIVATE HpackOutputStream {
+ public:
+  HpackOutputStream();
+  HpackOutputStream(const HpackOutputStream&) = delete;
+  HpackOutputStream& operator=(const HpackOutputStream&) = delete;
+  ~HpackOutputStream();
+
+  // Appends the lower |bit_size| bits of |bits| to the internal buffer.
+  //
+  // |bit_size| must be > 0 and <= 8. |bits| must not have any bits
+  // set other than the lower |bit_size| bits.
+  void AppendBits(uint8_t bits, size_t bit_size);
+
+  // Simply forwards to AppendBits(prefix.bits, prefix.bit-size).
+  void AppendPrefix(HpackPrefix prefix);
+
+  // Directly appends |buffer|.
+  void AppendBytes(SpdyStringPiece buffer);
+
+  // Appends the given integer using the representation described in
+  // 6.1. If the internal buffer ends on a byte boundary, the prefix
+  // length N is taken to be 8; otherwise, it is taken to be the
+  // number of bits to the next byte boundary.
+  //
+  // It is guaranteed that the internal buffer will end on a byte
+  // boundary after this function is called.
+  void AppendUint32(uint32_t I);
+
+  // Swaps the internal buffer with |output|, then resets state.
+  void TakeString(SpdyString* output);
+
+  // Gives up to |max_size| bytes of the internal buffer to |output|. Resets
+  // internal state with the overflow.
+  void BoundedTakeString(size_t max_size, SpdyString* output);
+
+  // Size in bytes of stream's internal buffer.
+  size_t size() const { return buffer_.size(); }
+
+  // Returns the estimate of dynamically allocated memory in bytes.
+  size_t EstimateMemoryUsage() const;
+
+ private:
+  // The internal bit buffer.
+  SpdyString buffer_;
+
+  // If 0, the buffer ends on a byte boundary. If non-zero, the buffer
+  // ends on the nth most significant bit. Guaranteed to be < 8.
+  size_t bit_offset_;
+};
+
+}  // namespace spdy
+
+#endif  // QUICHE_SPDY_CORE_HPACK_HPACK_OUTPUT_STREAM_H_
diff --git a/spdy/core/hpack/hpack_output_stream_test.cc b/spdy/core/hpack/hpack_output_stream_test.cc
new file mode 100644
index 0000000..823c41b
--- /dev/null
+++ b/spdy/core/hpack/hpack_output_stream_test.cc
@@ -0,0 +1,276 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_output_stream.h"
+
+#include <cstddef>
+
+#include "testing/gtest/include/gtest/gtest.h"
+
+namespace spdy {
+
+namespace {
+
+// Make sure that AppendBits() appends bits starting from the most
+// significant bit, and that it can handle crossing a byte boundary.
+TEST(HpackOutputStreamTest, AppendBits) {
+  HpackOutputStream output_stream;
+  SpdyString expected_str;
+
+  output_stream.AppendBits(0x1, 1);
+  expected_str.append(1, 0x00);
+  expected_str.back() |= (0x1 << 7);
+
+  output_stream.AppendBits(0x0, 1);
+
+  output_stream.AppendBits(0x3, 2);
+  *expected_str.rbegin() |= (0x3 << 4);
+
+  output_stream.AppendBits(0x0, 2);
+
+  // Byte-crossing append.
+  output_stream.AppendBits(0x7, 3);
+  *expected_str.rbegin() |= (0x7 >> 1);
+  expected_str.append(1, 0x00);
+  expected_str.back() |= (0x7 << 7);
+
+  output_stream.AppendBits(0x0, 7);
+
+  SpdyString str;
+  output_stream.TakeString(&str);
+  EXPECT_EQ(expected_str, str);
+}
+
+// Utility function to return I as a string encoded with an N-bit
+// prefix.
+SpdyString EncodeUint32(uint8_t N, uint32_t I) {
+  HpackOutputStream output_stream;
+  if (N < 8) {
+    output_stream.AppendBits(0x00, 8 - N);
+  }
+  output_stream.AppendUint32(I);
+  SpdyString str;
+  output_stream.TakeString(&str);
+  return str;
+}
+
+// The {Number}ByteIntegersEightBitPrefix tests below test that
+// certain integers are encoded correctly with an 8-bit prefix in
+// exactly {Number} bytes.
+
+TEST(HpackOutputStreamTest, OneByteIntegersEightBitPrefix) {
+  // Minimum.
+  EXPECT_EQ(SpdyString("\x00", 1), EncodeUint32(8, 0x00));
+  EXPECT_EQ("\x7f", EncodeUint32(8, 0x7f));
+  // Maximum.
+  EXPECT_EQ("\xfe", EncodeUint32(8, 0xfe));
+}
+
+TEST(HpackOutputStreamTest, TwoByteIntegersEightBitPrefix) {
+  // Minimum.
+  EXPECT_EQ(SpdyString("\xff\x00", 2), EncodeUint32(8, 0xff));
+  EXPECT_EQ("\xff\x01", EncodeUint32(8, 0x0100));
+  // Maximum.
+  EXPECT_EQ("\xff\x7f", EncodeUint32(8, 0x017e));
+}
+
+TEST(HpackOutputStreamTest, ThreeByteIntegersEightBitPrefix) {
+  // Minimum.
+  EXPECT_EQ("\xff\x80\x01", EncodeUint32(8, 0x017f));
+  EXPECT_EQ("\xff\x80\x1e", EncodeUint32(8, 0x0fff));
+  // Maximum.
+  EXPECT_EQ("\xff\xff\x7f", EncodeUint32(8, 0x40fe));
+}
+
+TEST(HpackOutputStreamTest, FourByteIntegersEightBitPrefix) {
+  // Minimum.
+  EXPECT_EQ("\xff\x80\x80\x01", EncodeUint32(8, 0x40ff));
+  EXPECT_EQ("\xff\x80\xfe\x03", EncodeUint32(8, 0xffff));
+  // Maximum.
+  EXPECT_EQ("\xff\xff\xff\x7f", EncodeUint32(8, 0x002000fe));
+}
+
+TEST(HpackOutputStreamTest, FiveByteIntegersEightBitPrefix) {
+  // Minimum.
+  EXPECT_EQ("\xff\x80\x80\x80\x01", EncodeUint32(8, 0x002000ff));
+  EXPECT_EQ("\xff\x80\xfe\xff\x07", EncodeUint32(8, 0x00ffffff));
+  // Maximum.
+  EXPECT_EQ("\xff\xff\xff\xff\x7f", EncodeUint32(8, 0x100000fe));
+}
+
+TEST(HpackOutputStreamTest, SixByteIntegersEightBitPrefix) {
+  // Minimum.
+  EXPECT_EQ("\xff\x80\x80\x80\x80\x01", EncodeUint32(8, 0x100000ff));
+  // Maximum.
+  EXPECT_EQ("\xff\x80\xfe\xff\xff\x0f", EncodeUint32(8, 0xffffffff));
+}
+
+// The {Number}ByteIntegersOneToSevenBitPrefix tests below test that
+// certain integers are encoded correctly with an N-bit prefix in
+// exactly {Number} bytes for N in {1, 2, ..., 7}.
+
+TEST(HpackOutputStreamTest, OneByteIntegersOneToSevenBitPrefixes) {
+  // Minimums.
+  EXPECT_EQ(SpdyString("\x00", 1), EncodeUint32(7, 0x00));
+  EXPECT_EQ(SpdyString("\x00", 1), EncodeUint32(6, 0x00));
+  EXPECT_EQ(SpdyString("\x00", 1), EncodeUint32(5, 0x00));
+  EXPECT_EQ(SpdyString("\x00", 1), EncodeUint32(4, 0x00));
+  EXPECT_EQ(SpdyString("\x00", 1), EncodeUint32(3, 0x00));
+  EXPECT_EQ(SpdyString("\x00", 1), EncodeUint32(2, 0x00));
+  EXPECT_EQ(SpdyString("\x00", 1), EncodeUint32(1, 0x00));
+
+  // Maximums.
+  EXPECT_EQ("\x7e", EncodeUint32(7, 0x7e));
+  EXPECT_EQ("\x3e", EncodeUint32(6, 0x3e));
+  EXPECT_EQ("\x1e", EncodeUint32(5, 0x1e));
+  EXPECT_EQ("\x0e", EncodeUint32(4, 0x0e));
+  EXPECT_EQ("\x06", EncodeUint32(3, 0x06));
+  EXPECT_EQ("\x02", EncodeUint32(2, 0x02));
+  EXPECT_EQ(SpdyString("\x00", 1), EncodeUint32(1, 0x00));
+}
+
+TEST(HpackOutputStreamTest, TwoByteIntegersOneToSevenBitPrefixes) {
+  // Minimums.
+  EXPECT_EQ(SpdyString("\x7f\x00", 2), EncodeUint32(7, 0x7f));
+  EXPECT_EQ(SpdyString("\x3f\x00", 2), EncodeUint32(6, 0x3f));
+  EXPECT_EQ(SpdyString("\x1f\x00", 2), EncodeUint32(5, 0x1f));
+  EXPECT_EQ(SpdyString("\x0f\x00", 2), EncodeUint32(4, 0x0f));
+  EXPECT_EQ(SpdyString("\x07\x00", 2), EncodeUint32(3, 0x07));
+  EXPECT_EQ(SpdyString("\x03\x00", 2), EncodeUint32(2, 0x03));
+  EXPECT_EQ(SpdyString("\x01\x00", 2), EncodeUint32(1, 0x01));
+
+  // Maximums.
+  EXPECT_EQ("\x7f\x7f", EncodeUint32(7, 0xfe));
+  EXPECT_EQ("\x3f\x7f", EncodeUint32(6, 0xbe));
+  EXPECT_EQ("\x1f\x7f", EncodeUint32(5, 0x9e));
+  EXPECT_EQ("\x0f\x7f", EncodeUint32(4, 0x8e));
+  EXPECT_EQ("\x07\x7f", EncodeUint32(3, 0x86));
+  EXPECT_EQ("\x03\x7f", EncodeUint32(2, 0x82));
+  EXPECT_EQ("\x01\x7f", EncodeUint32(1, 0x80));
+}
+
+TEST(HpackOutputStreamTest, ThreeByteIntegersOneToSevenBitPrefixes) {
+  // Minimums.
+  EXPECT_EQ("\x7f\x80\x01", EncodeUint32(7, 0xff));
+  EXPECT_EQ("\x3f\x80\x01", EncodeUint32(6, 0xbf));
+  EXPECT_EQ("\x1f\x80\x01", EncodeUint32(5, 0x9f));
+  EXPECT_EQ("\x0f\x80\x01", EncodeUint32(4, 0x8f));
+  EXPECT_EQ("\x07\x80\x01", EncodeUint32(3, 0x87));
+  EXPECT_EQ("\x03\x80\x01", EncodeUint32(2, 0x83));
+  EXPECT_EQ("\x01\x80\x01", EncodeUint32(1, 0x81));
+
+  // Maximums.
+  EXPECT_EQ("\x7f\xff\x7f", EncodeUint32(7, 0x407e));
+  EXPECT_EQ("\x3f\xff\x7f", EncodeUint32(6, 0x403e));
+  EXPECT_EQ("\x1f\xff\x7f", EncodeUint32(5, 0x401e));
+  EXPECT_EQ("\x0f\xff\x7f", EncodeUint32(4, 0x400e));
+  EXPECT_EQ("\x07\xff\x7f", EncodeUint32(3, 0x4006));
+  EXPECT_EQ("\x03\xff\x7f", EncodeUint32(2, 0x4002));
+  EXPECT_EQ("\x01\xff\x7f", EncodeUint32(1, 0x4000));
+}
+
+TEST(HpackOutputStreamTest, FourByteIntegersOneToSevenBitPrefixes) {
+  // Minimums.
+  EXPECT_EQ("\x7f\x80\x80\x01", EncodeUint32(7, 0x407f));
+  EXPECT_EQ("\x3f\x80\x80\x01", EncodeUint32(6, 0x403f));
+  EXPECT_EQ("\x1f\x80\x80\x01", EncodeUint32(5, 0x401f));
+  EXPECT_EQ("\x0f\x80\x80\x01", EncodeUint32(4, 0x400f));
+  EXPECT_EQ("\x07\x80\x80\x01", EncodeUint32(3, 0x4007));
+  EXPECT_EQ("\x03\x80\x80\x01", EncodeUint32(2, 0x4003));
+  EXPECT_EQ("\x01\x80\x80\x01", EncodeUint32(1, 0x4001));
+
+  // Maximums.
+  EXPECT_EQ("\x7f\xff\xff\x7f", EncodeUint32(7, 0x20007e));
+  EXPECT_EQ("\x3f\xff\xff\x7f", EncodeUint32(6, 0x20003e));
+  EXPECT_EQ("\x1f\xff\xff\x7f", EncodeUint32(5, 0x20001e));
+  EXPECT_EQ("\x0f\xff\xff\x7f", EncodeUint32(4, 0x20000e));
+  EXPECT_EQ("\x07\xff\xff\x7f", EncodeUint32(3, 0x200006));
+  EXPECT_EQ("\x03\xff\xff\x7f", EncodeUint32(2, 0x200002));
+  EXPECT_EQ("\x01\xff\xff\x7f", EncodeUint32(1, 0x200000));
+}
+
+TEST(HpackOutputStreamTest, FiveByteIntegersOneToSevenBitPrefixes) {
+  // Minimums.
+  EXPECT_EQ("\x7f\x80\x80\x80\x01", EncodeUint32(7, 0x20007f));
+  EXPECT_EQ("\x3f\x80\x80\x80\x01", EncodeUint32(6, 0x20003f));
+  EXPECT_EQ("\x1f\x80\x80\x80\x01", EncodeUint32(5, 0x20001f));
+  EXPECT_EQ("\x0f\x80\x80\x80\x01", EncodeUint32(4, 0x20000f));
+  EXPECT_EQ("\x07\x80\x80\x80\x01", EncodeUint32(3, 0x200007));
+  EXPECT_EQ("\x03\x80\x80\x80\x01", EncodeUint32(2, 0x200003));
+  EXPECT_EQ("\x01\x80\x80\x80\x01", EncodeUint32(1, 0x200001));
+
+  // Maximums.
+  EXPECT_EQ("\x7f\xff\xff\xff\x7f", EncodeUint32(7, 0x1000007e));
+  EXPECT_EQ("\x3f\xff\xff\xff\x7f", EncodeUint32(6, 0x1000003e));
+  EXPECT_EQ("\x1f\xff\xff\xff\x7f", EncodeUint32(5, 0x1000001e));
+  EXPECT_EQ("\x0f\xff\xff\xff\x7f", EncodeUint32(4, 0x1000000e));
+  EXPECT_EQ("\x07\xff\xff\xff\x7f", EncodeUint32(3, 0x10000006));
+  EXPECT_EQ("\x03\xff\xff\xff\x7f", EncodeUint32(2, 0x10000002));
+  EXPECT_EQ("\x01\xff\xff\xff\x7f", EncodeUint32(1, 0x10000000));
+}
+
+TEST(HpackOutputStreamTest, SixByteIntegersOneToSevenBitPrefixes) {
+  // Minimums.
+  EXPECT_EQ("\x7f\x80\x80\x80\x80\x01", EncodeUint32(7, 0x1000007f));
+  EXPECT_EQ("\x3f\x80\x80\x80\x80\x01", EncodeUint32(6, 0x1000003f));
+  EXPECT_EQ("\x1f\x80\x80\x80\x80\x01", EncodeUint32(5, 0x1000001f));
+  EXPECT_EQ("\x0f\x80\x80\x80\x80\x01", EncodeUint32(4, 0x1000000f));
+  EXPECT_EQ("\x07\x80\x80\x80\x80\x01", EncodeUint32(3, 0x10000007));
+  EXPECT_EQ("\x03\x80\x80\x80\x80\x01", EncodeUint32(2, 0x10000003));
+  EXPECT_EQ("\x01\x80\x80\x80\x80\x01", EncodeUint32(1, 0x10000001));
+
+  // Maximums.
+  EXPECT_EQ("\x7f\x80\xff\xff\xff\x0f", EncodeUint32(7, 0xffffffff));
+  EXPECT_EQ("\x3f\xc0\xff\xff\xff\x0f", EncodeUint32(6, 0xffffffff));
+  EXPECT_EQ("\x1f\xe0\xff\xff\xff\x0f", EncodeUint32(5, 0xffffffff));
+  EXPECT_EQ("\x0f\xf0\xff\xff\xff\x0f", EncodeUint32(4, 0xffffffff));
+  EXPECT_EQ("\x07\xf8\xff\xff\xff\x0f", EncodeUint32(3, 0xffffffff));
+  EXPECT_EQ("\x03\xfc\xff\xff\xff\x0f", EncodeUint32(2, 0xffffffff));
+  EXPECT_EQ("\x01\xfe\xff\xff\xff\x0f", EncodeUint32(1, 0xffffffff));
+}
+
+// Test that encoding an integer with an N-bit prefix preserves the
+// upper (8-N) bits of the first byte.
+TEST(HpackOutputStreamTest, AppendUint32PreservesUpperBits) {
+  HpackOutputStream output_stream;
+  output_stream.AppendBits(0x7f, 7);
+  output_stream.AppendUint32(0x01);
+  SpdyString str;
+  output_stream.TakeString(&str);
+  EXPECT_EQ(SpdyString("\xff\x00", 2), str);
+}
+
+TEST(HpackOutputStreamTest, AppendBytes) {
+  HpackOutputStream output_stream;
+
+  output_stream.AppendBytes("buffer1");
+  output_stream.AppendBytes("buffer2");
+
+  SpdyString str;
+  output_stream.TakeString(&str);
+  EXPECT_EQ("buffer1buffer2", str);
+}
+
+TEST(HpackOutputStreamTest, BoundedTakeString) {
+  HpackOutputStream output_stream;
+
+  output_stream.AppendBytes("buffer12");
+  output_stream.AppendBytes("buffer456");
+
+  SpdyString str;
+  output_stream.BoundedTakeString(9, &str);
+  EXPECT_EQ("buffer12b", str);
+
+  output_stream.AppendBits(0x7f, 7);
+  output_stream.AppendUint32(0x11);
+  output_stream.BoundedTakeString(9, &str);
+  EXPECT_EQ("uffer456\xff", str);
+
+  output_stream.BoundedTakeString(9, &str);
+  EXPECT_EQ("\x10", str);
+}
+
+}  // namespace
+
+}  // namespace spdy
diff --git a/spdy/core/hpack/hpack_round_trip_test.cc b/spdy/core/hpack/hpack_round_trip_test.cc
new file mode 100644
index 0000000..4b3a848
--- /dev/null
+++ b/spdy/core/hpack/hpack_round_trip_test.cc
@@ -0,0 +1,227 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include <cmath>
+#include <cstdint>
+#include <ctime>
+#include <vector>
+
+#include "testing/gtest/include/gtest/gtest.h"
+#include "net/third_party/quiche/src/http2/test_tools/http2_random.h"
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_constants.h"
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_decoder_adapter.h"
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_encoder.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_test_utils.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string.h"
+
+namespace spdy {
+namespace test {
+
+namespace {
+
+// Supports testing with the input split at every byte boundary.
+enum InputSizeParam { ALL_INPUT, ONE_BYTE, ZERO_THEN_ONE_BYTE };
+
+class HpackRoundTripTest : public ::testing::TestWithParam<InputSizeParam> {
+ protected:
+  HpackRoundTripTest() : encoder_(ObtainHpackHuffmanTable()), decoder_() {}
+
+  void SetUp() override {
+    // Use a small table size to tickle eviction handling.
+    encoder_.ApplyHeaderTableSizeSetting(256);
+    decoder_.ApplyHeaderTableSizeSetting(256);
+  }
+
+  bool RoundTrip(const SpdyHeaderBlock& header_set) {
+    SpdyString encoded;
+    encoder_.EncodeHeaderSet(header_set, &encoded);
+
+    bool success = true;
+    if (GetParam() == ALL_INPUT) {
+      // Pass all the input to the decoder at once.
+      success = decoder_.HandleControlFrameHeadersData(encoded.data(),
+                                                       encoded.size());
+    } else if (GetParam() == ONE_BYTE) {
+      // Pass the input to the decoder one byte at a time.
+      const char* data = encoded.data();
+      for (size_t ndx = 0; ndx < encoded.size() && success; ++ndx) {
+        success = decoder_.HandleControlFrameHeadersData(data + ndx, 1);
+      }
+    } else if (GetParam() == ZERO_THEN_ONE_BYTE) {
+      // Pass the input to the decoder one byte at a time, but before each
+      // byte pass an empty buffer.
+      const char* data = encoded.data();
+      for (size_t ndx = 0; ndx < encoded.size() && success; ++ndx) {
+        success = (decoder_.HandleControlFrameHeadersData(data + ndx, 0) &&
+                   decoder_.HandleControlFrameHeadersData(data + ndx, 1));
+      }
+    } else {
+      ADD_FAILURE() << "Unknown param: " << GetParam();
+    }
+
+    if (success) {
+      success = decoder_.HandleControlFrameHeadersComplete(nullptr);
+    }
+
+    EXPECT_EQ(header_set, decoder_.decoded_block());
+    return success;
+  }
+
+  size_t SampleExponential(size_t mean, size_t sanity_bound) {
+    return std::min<size_t>(-std::log(random_.RandDouble()) * mean,
+                            sanity_bound);
+  }
+
+  http2::test::Http2Random random_;
+  HpackEncoder encoder_;
+  HpackDecoderAdapter decoder_;
+};
+
+INSTANTIATE_TEST_CASE_P(Tests,
+                        HpackRoundTripTest,
+                        ::testing::Values(ALL_INPUT,
+                                          ONE_BYTE,
+                                          ZERO_THEN_ONE_BYTE));
+
+TEST_P(HpackRoundTripTest, ResponseFixtures) {
+  {
+    SpdyHeaderBlock headers;
+    headers[":status"] = "302";
+    headers["cache-control"] = "private";
+    headers["date"] = "Mon, 21 Oct 2013 20:13:21 GMT";
+    headers["location"] = "https://www.example.com";
+    EXPECT_TRUE(RoundTrip(headers));
+  }
+  {
+    SpdyHeaderBlock headers;
+    headers[":status"] = "200";
+    headers["cache-control"] = "private";
+    headers["date"] = "Mon, 21 Oct 2013 20:13:21 GMT";
+    headers["location"] = "https://www.example.com";
+    EXPECT_TRUE(RoundTrip(headers));
+  }
+  {
+    SpdyHeaderBlock headers;
+    headers[":status"] = "200";
+    headers["cache-control"] = "private";
+    headers["content-encoding"] = "gzip";
+    headers["date"] = "Mon, 21 Oct 2013 20:13:22 GMT";
+    headers["location"] = "https://www.example.com";
+    headers["set-cookie"] =
+        "foo=ASDJKHQKBZXOQWEOPIUAXQWEOIU;"
+        " max-age=3600; version=1";
+    headers["multivalue"] = SpdyString("foo\0bar", 7);
+    EXPECT_TRUE(RoundTrip(headers));
+  }
+}
+
+TEST_P(HpackRoundTripTest, RequestFixtures) {
+  {
+    SpdyHeaderBlock headers;
+    headers[":authority"] = "www.example.com";
+    headers[":method"] = "GET";
+    headers[":path"] = "/";
+    headers[":scheme"] = "http";
+    headers["cookie"] = "baz=bing; foo=bar";
+    EXPECT_TRUE(RoundTrip(headers));
+  }
+  {
+    SpdyHeaderBlock headers;
+    headers[":authority"] = "www.example.com";
+    headers[":method"] = "GET";
+    headers[":path"] = "/";
+    headers[":scheme"] = "http";
+    headers["cache-control"] = "no-cache";
+    headers["cookie"] = "foo=bar; spam=eggs";
+    EXPECT_TRUE(RoundTrip(headers));
+  }
+  {
+    SpdyHeaderBlock headers;
+    headers[":authority"] = "www.example.com";
+    headers[":method"] = "GET";
+    headers[":path"] = "/index.html";
+    headers[":scheme"] = "https";
+    headers["custom-key"] = "custom-value";
+    headers["cookie"] = "baz=bing; fizzle=fazzle; garbage";
+    headers["multivalue"] = SpdyString("foo\0bar", 7);
+    EXPECT_TRUE(RoundTrip(headers));
+  }
+}
+
+TEST_P(HpackRoundTripTest, RandomizedExamples) {
+  // Grow vectors of names & values, which are seeded with fixtures and then
+  // expanded with dynamically generated data. Samples are taken using the
+  // exponential distribution.
+  std::vector<SpdyString> pseudo_header_names, random_header_names;
+  pseudo_header_names.push_back(":authority");
+  pseudo_header_names.push_back(":path");
+  pseudo_header_names.push_back(":status");
+
+  // TODO(jgraettinger): Enable "cookie" as a name fixture. Crumbs may be
+  // reconstructed in any order, which breaks the simple validation used here.
+
+  std::vector<SpdyString> values;
+  values.push_back("/");
+  values.push_back("/index.html");
+  values.push_back("200");
+  values.push_back("404");
+  values.push_back("");
+  values.push_back("baz=bing; foo=bar; garbage");
+  values.push_back("baz=bing; fizzle=fazzle; garbage");
+
+  for (size_t i = 0; i != 2000; ++i) {
+    SpdyHeaderBlock headers;
+
+    // Choose a random number of headers to add, and of these a random subset
+    // will be HTTP/2 pseudo headers.
+    size_t header_count = 1 + SampleExponential(7, 50);
+    size_t pseudo_header_count =
+        std::min(header_count, 1 + SampleExponential(7, 50));
+    EXPECT_LE(pseudo_header_count, header_count);
+    for (size_t j = 0; j != header_count; ++j) {
+      SpdyString name, value;
+      // Pseudo headers must be added before regular headers.
+      if (j < pseudo_header_count) {
+        // Choose one of the defined pseudo headers at random.
+        size_t name_index = random_.Uniform(pseudo_header_names.size());
+        name = pseudo_header_names[name_index];
+      } else {
+        // Randomly reuse an existing header name, or generate a new one.
+        size_t name_index = SampleExponential(20, 200);
+        if (name_index >= random_header_names.size()) {
+          name = random_.RandString(1 + SampleExponential(5, 30));
+          // A regular header cannot begin with the pseudo header prefix ":".
+          if (name[0] == ':') {
+            name[0] = 'x';
+          }
+          random_header_names.push_back(name);
+        } else {
+          name = random_header_names[name_index];
+        }
+      }
+
+      // Randomly reuse an existing value, or generate a new one.
+      size_t value_index = SampleExponential(20, 200);
+      if (value_index >= values.size()) {
+        SpdyString newvalue = random_.RandString(1 + SampleExponential(15, 75));
+        // Currently order is not preserved in the encoder.  In particular,
+        // when a value is decomposed at \0 delimiters, its parts might get
+        // encoded out of order if some but not all of them already exist in
+        // the header table.  For now, avoid \0 bytes in values.
+        std::replace(newvalue.begin(), newvalue.end(), '\x00', '\x01');
+        values.push_back(newvalue);
+        value = values.back();
+      } else {
+        value = values[value_index];
+      }
+      headers[name] = value;
+    }
+    EXPECT_TRUE(RoundTrip(headers));
+  }
+}
+
+}  // namespace
+
+}  // namespace test
+}  // namespace spdy
diff --git a/spdy/core/hpack/hpack_static_table.cc b/spdy/core/hpack/hpack_static_table.cc
new file mode 100644
index 0000000..14e282e
--- /dev/null
+++ b/spdy/core/hpack/hpack_static_table.cc
@@ -0,0 +1,50 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_static_table.h"
+
+#include "base/logging.h"
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_constants.h"
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_entry.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_estimate_memory_usage.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string_piece.h"
+
+namespace spdy {
+
+HpackStaticTable::HpackStaticTable() = default;
+
+HpackStaticTable::~HpackStaticTable() = default;
+
+void HpackStaticTable::Initialize(const HpackStaticEntry* static_entry_table,
+                                  size_t static_entry_count) {
+  CHECK(!IsInitialized());
+
+  int total_insertions = 0;
+  for (const HpackStaticEntry* it = static_entry_table;
+       it != static_entry_table + static_entry_count; ++it) {
+    static_entries_.push_back(
+        HpackEntry(SpdyStringPiece(it->name, it->name_len),
+                   SpdyStringPiece(it->value, it->value_len),
+                   true,  // is_static
+                   total_insertions));
+    HpackEntry* entry = &static_entries_.back();
+    CHECK(static_index_.insert(entry).second);
+    // Multiple static entries may have the same name, so inserts may fail.
+    static_name_index_.insert(std::make_pair(entry->name(), entry));
+
+    ++total_insertions;
+  }
+}
+
+bool HpackStaticTable::IsInitialized() const {
+  return !static_entries_.empty();
+}
+
+size_t HpackStaticTable::EstimateMemoryUsage() const {
+  return SpdyEstimateMemoryUsage(static_entries_) +
+         SpdyEstimateMemoryUsage(static_index_) +
+         SpdyEstimateMemoryUsage(static_name_index_);
+}
+
+}  // namespace spdy
diff --git a/spdy/core/hpack/hpack_static_table.h b/spdy/core/hpack/hpack_static_table.h
new file mode 100644
index 0000000..f354a12
--- /dev/null
+++ b/spdy/core/hpack/hpack_static_table.h
@@ -0,0 +1,54 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef QUICHE_SPDY_CORE_HPACK_HPACK_STATIC_TABLE_H_
+#define QUICHE_SPDY_CORE_HPACK_HPACK_STATIC_TABLE_H_
+
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_header_table.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_export.h"
+
+namespace spdy {
+
+struct HpackStaticEntry;
+
+// HpackStaticTable provides |static_entries_| and |static_index_| for HPACK
+// encoding and decoding contexts.  Once initialized, an instance is read only
+// and may be accessed only through its const interface.  Such an instance may
+// be shared accross multiple HPACK contexts.
+class SPDY_EXPORT_PRIVATE HpackStaticTable {
+ public:
+  HpackStaticTable();
+  ~HpackStaticTable();
+
+  // Prepares HpackStaticTable by filling up static_entries_ and static_index_
+  // from an array of struct HpackStaticEntry.  Must be called exactly once.
+  void Initialize(const HpackStaticEntry* static_entry_table,
+                  size_t static_entry_count);
+
+  // Returns whether Initialize() has been called.
+  bool IsInitialized() const;
+
+  // Accessors.
+  const HpackHeaderTable::EntryTable& GetStaticEntries() const {
+    return static_entries_;
+  }
+  const HpackHeaderTable::UnorderedEntrySet& GetStaticIndex() const {
+    return static_index_;
+  }
+  const HpackHeaderTable::NameToEntryMap& GetStaticNameIndex() const {
+    return static_name_index_;
+  }
+
+  // Returns the estimate of dynamically allocated memory in bytes.
+  size_t EstimateMemoryUsage() const;
+
+ private:
+  HpackHeaderTable::EntryTable static_entries_;
+  HpackHeaderTable::UnorderedEntrySet static_index_;
+  HpackHeaderTable::NameToEntryMap static_name_index_;
+};
+
+}  // namespace spdy
+
+#endif  // QUICHE_SPDY_CORE_HPACK_HPACK_STATIC_TABLE_H_
diff --git a/spdy/core/hpack/hpack_static_table_test.cc b/spdy/core/hpack/hpack_static_table_test.cc
new file mode 100644
index 0000000..4550be0
--- /dev/null
+++ b/spdy/core/hpack/hpack_static_table_test.cc
@@ -0,0 +1,60 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_static_table.h"
+
+#include <set>
+#include <vector>
+
+#include "testing/gtest/include/gtest/gtest.h"
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_constants.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string_piece.h"
+
+namespace spdy {
+
+namespace test {
+
+namespace {
+
+class HpackStaticTableTest : public ::testing::Test {
+ protected:
+  HpackStaticTableTest() : table_() {}
+
+  HpackStaticTable table_;
+};
+
+// Check that an initialized instance has the right number of entries.
+TEST_F(HpackStaticTableTest, Initialize) {
+  EXPECT_FALSE(table_.IsInitialized());
+  table_.Initialize(HpackStaticTableVector().data(),
+                    HpackStaticTableVector().size());
+  EXPECT_TRUE(table_.IsInitialized());
+
+  HpackHeaderTable::EntryTable static_entries = table_.GetStaticEntries();
+  EXPECT_EQ(HpackStaticTableVector().size(), static_entries.size());
+
+  HpackHeaderTable::UnorderedEntrySet static_index = table_.GetStaticIndex();
+  EXPECT_EQ(HpackStaticTableVector().size(), static_index.size());
+
+  HpackHeaderTable::NameToEntryMap static_name_index =
+      table_.GetStaticNameIndex();
+  std::set<SpdyStringPiece> names;
+  for (auto* entry : static_index) {
+    names.insert(entry->name());
+  }
+  EXPECT_EQ(names.size(), static_name_index.size());
+}
+
+// Test that ObtainHpackStaticTable returns the same instance every time.
+TEST_F(HpackStaticTableTest, IsSingleton) {
+  const HpackStaticTable* static_table_one = &ObtainHpackStaticTable();
+  const HpackStaticTable* static_table_two = &ObtainHpackStaticTable();
+  EXPECT_EQ(static_table_one, static_table_two);
+}
+
+}  // namespace
+
+}  // namespace test
+
+}  // namespace spdy
diff --git a/spdy/core/http2_frame_decoder_adapter.cc b/spdy/core/http2_frame_decoder_adapter.cc
new file mode 100644
index 0000000..c4e728d
--- /dev/null
+++ b/spdy/core/http2_frame_decoder_adapter.cc
@@ -0,0 +1,1022 @@
+// Copyright 2016 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "net/third_party/quiche/src/spdy/core/http2_frame_decoder_adapter.h"
+
+// Logging policy: If an error in the input is detected, VLOG(n) is used so that
+// the option exists to debug the situation. Otherwise, this code mostly uses
+// DVLOG so that the logging does not slow down production code when things are
+// working OK.
+
+#include <stddef.h>
+
+#include <cstdint>
+#include <cstring>
+#include <utility>
+
+#include "base/logging.h"
+#include "net/third_party/quiche/src/http2/decoder/decode_buffer.h"
+#include "net/third_party/quiche/src/http2/decoder/decode_status.h"
+#include "net/third_party/quiche/src/http2/decoder/http2_frame_decoder.h"
+#include "net/third_party/quiche/src/http2/decoder/http2_frame_decoder_listener.h"
+#include "net/third_party/quiche/src/http2/http2_constants.h"
+#include "net/third_party/quiche/src/http2/http2_structures.h"
+#include "net/third_party/quiche/src/http2/platform/api/http2_string.h"
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_decoder_adapter.h"
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_header_table.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_alt_svc_wire_format.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_header_block.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_headers_handler_interface.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_protocol.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_bug_tracker.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_endianness_util.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_estimate_memory_usage.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_flags.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_ptr_util.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string_utils.h"
+
+using ::spdy::ExtensionVisitorInterface;
+using ::spdy::HpackDecoderAdapter;
+using ::spdy::HpackHeaderTable;
+using ::spdy::ParseErrorCode;
+using ::spdy::ParseFrameType;
+using ::spdy::SpdyAltSvcWireFormat;
+using ::spdy::SpdyErrorCode;
+using ::spdy::SpdyEstimateMemoryUsage;
+using ::spdy::SpdyFramerDebugVisitorInterface;
+using ::spdy::SpdyFramerVisitorInterface;
+using ::spdy::SpdyFrameType;
+using ::spdy::SpdyHeadersHandlerInterface;
+using ::spdy::SpdyKnownSettingsId;
+using ::spdy::SpdyMakeUnique;
+using ::spdy::SpdySettingsId;
+
+namespace http2 {
+namespace {
+
+const bool kHasPriorityFields = true;
+const bool kNotHasPriorityFields = false;
+
+bool IsPaddable(Http2FrameType type) {
+  return type == Http2FrameType::DATA || type == Http2FrameType::HEADERS ||
+         type == Http2FrameType::PUSH_PROMISE;
+}
+
+SpdyFrameType ToSpdyFrameType(Http2FrameType type) {
+  return ParseFrameType(static_cast<uint8_t>(type));
+}
+
+uint64_t ToSpdyPingId(const Http2PingFields& ping) {
+  uint64_t v;
+  std::memcpy(&v, ping.opaque_bytes, Http2PingFields::EncodedSize());
+  return spdy::SpdyNetToHost64(v);
+}
+
+// Overwrites the fields of the header with invalid values, for the purpose
+// of identifying reading of unset fields. Only takes effect for debug builds.
+// In Address Sanatizer builds, it also marks the fields as un-readable.
+void CorruptFrameHeader(Http2FrameHeader* header) {
+#ifndef NDEBUG
+  // Beyond a valid payload length, which is 2^24 - 1.
+  header->payload_length = 0x1010dead;
+  // An unsupported frame type.
+  header->type = Http2FrameType(0x80);
+  DCHECK(!IsSupportedHttp2FrameType(header->type));
+  // Frame flag bits that aren't used by any supported frame type.
+  header->flags = Http2FrameFlag(0xd2);
+  // A stream id with the reserved high-bit (R in the RFC) set.
+  // 2129510127 when the high-bit is cleared.
+  header->stream_id = 0xfeedbeef;
+#endif
+}
+
+}  // namespace
+
+const char* Http2DecoderAdapter::StateToString(int state) {
+  switch (state) {
+    case SPDY_ERROR:
+      return "ERROR";
+    case SPDY_FRAME_COMPLETE:
+      return "FRAME_COMPLETE";
+    case SPDY_READY_FOR_FRAME:
+      return "READY_FOR_FRAME";
+    case SPDY_READING_COMMON_HEADER:
+      return "READING_COMMON_HEADER";
+    case SPDY_CONTROL_FRAME_PAYLOAD:
+      return "CONTROL_FRAME_PAYLOAD";
+    case SPDY_READ_DATA_FRAME_PADDING_LENGTH:
+      return "SPDY_READ_DATA_FRAME_PADDING_LENGTH";
+    case SPDY_CONSUME_PADDING:
+      return "SPDY_CONSUME_PADDING";
+    case SPDY_IGNORE_REMAINING_PAYLOAD:
+      return "IGNORE_REMAINING_PAYLOAD";
+    case SPDY_FORWARD_STREAM_FRAME:
+      return "FORWARD_STREAM_FRAME";
+    case SPDY_CONTROL_FRAME_BEFORE_HEADER_BLOCK:
+      return "SPDY_CONTROL_FRAME_BEFORE_HEADER_BLOCK";
+    case SPDY_CONTROL_FRAME_HEADER_BLOCK:
+      return "SPDY_CONTROL_FRAME_HEADER_BLOCK";
+    case SPDY_GOAWAY_FRAME_PAYLOAD:
+      return "SPDY_GOAWAY_FRAME_PAYLOAD";
+    case SPDY_SETTINGS_FRAME_HEADER:
+      return "SPDY_SETTINGS_FRAME_HEADER";
+    case SPDY_SETTINGS_FRAME_PAYLOAD:
+      return "SPDY_SETTINGS_FRAME_PAYLOAD";
+    case SPDY_ALTSVC_FRAME_PAYLOAD:
+      return "SPDY_ALTSVC_FRAME_PAYLOAD";
+  }
+  return "UNKNOWN_STATE";
+}
+
+const char* Http2DecoderAdapter::SpdyFramerErrorToString(
+    SpdyFramerError spdy_framer_error) {
+  switch (spdy_framer_error) {
+    case SPDY_NO_ERROR:
+      return "NO_ERROR";
+    case SPDY_INVALID_STREAM_ID:
+      return "INVALID_STREAM_ID";
+    case SPDY_INVALID_CONTROL_FRAME:
+      return "INVALID_CONTROL_FRAME";
+    case SPDY_CONTROL_PAYLOAD_TOO_LARGE:
+      return "CONTROL_PAYLOAD_TOO_LARGE";
+    case SPDY_ZLIB_INIT_FAILURE:
+      return "ZLIB_INIT_FAILURE";
+    case SPDY_UNSUPPORTED_VERSION:
+      return "UNSUPPORTED_VERSION";
+    case SPDY_DECOMPRESS_FAILURE:
+      return "DECOMPRESS_FAILURE";
+    case SPDY_COMPRESS_FAILURE:
+      return "COMPRESS_FAILURE";
+    case SPDY_GOAWAY_FRAME_CORRUPT:
+      return "GOAWAY_FRAME_CORRUPT";
+    case SPDY_RST_STREAM_FRAME_CORRUPT:
+      return "RST_STREAM_FRAME_CORRUPT";
+    case SPDY_INVALID_PADDING:
+      return "INVALID_PADDING";
+    case SPDY_INVALID_DATA_FRAME_FLAGS:
+      return "INVALID_DATA_FRAME_FLAGS";
+    case SPDY_INVALID_CONTROL_FRAME_FLAGS:
+      return "INVALID_CONTROL_FRAME_FLAGS";
+    case SPDY_UNEXPECTED_FRAME:
+      return "UNEXPECTED_FRAME";
+    case SPDY_INTERNAL_FRAMER_ERROR:
+      return "INTERNAL_FRAMER_ERROR";
+    case SPDY_INVALID_CONTROL_FRAME_SIZE:
+      return "INVALID_CONTROL_FRAME_SIZE";
+    case SPDY_OVERSIZED_PAYLOAD:
+      return "OVERSIZED_PAYLOAD";
+    case LAST_ERROR:
+      return "UNKNOWN_ERROR";
+  }
+  return "UNKNOWN_ERROR";
+}
+
+Http2DecoderAdapter::Http2DecoderAdapter() {
+  DVLOG(1) << "Http2DecoderAdapter ctor";
+  ResetInternal();
+}
+
+Http2DecoderAdapter::~Http2DecoderAdapter() = default;
+
+void Http2DecoderAdapter::set_visitor(SpdyFramerVisitorInterface* visitor) {
+  visitor_ = visitor;
+}
+
+void Http2DecoderAdapter::set_debug_visitor(
+    SpdyFramerDebugVisitorInterface* debug_visitor) {
+  debug_visitor_ = debug_visitor;
+}
+
+void Http2DecoderAdapter::set_process_single_input_frame(bool v) {
+  process_single_input_frame_ = v;
+}
+
+void Http2DecoderAdapter::set_extension_visitor(
+    ExtensionVisitorInterface* visitor) {
+  extension_ = visitor;
+}
+
+// Passes the call on to the HPACK decoder.
+void Http2DecoderAdapter::SetDecoderHeaderTableDebugVisitor(
+    std::unique_ptr<HpackHeaderTable::DebugVisitorInterface> visitor) {
+  GetHpackDecoder()->SetHeaderTableDebugVisitor(std::move(visitor));
+}
+
+size_t Http2DecoderAdapter::ProcessInput(const char* data, size_t len) {
+  size_t limit = recv_frame_size_limit_;
+  frame_decoder_->set_maximum_payload_size(limit);
+
+  size_t total_processed = 0;
+  while (len > 0 && spdy_state_ != SPDY_ERROR) {
+    // Process one at a time so that we update the adapter's internal
+    // state appropriately.
+    const size_t processed = ProcessInputFrame(data, len);
+
+    // We had some data, and weren't in an error state, so should have
+    // processed/consumed at least one byte of it, even if we then ended up
+    // in an error state.
+    DCHECK(processed > 0) << "processed=" << processed
+                          << "   spdy_state_=" << spdy_state_
+                          << "   spdy_framer_error_=" << spdy_framer_error_;
+
+    data += processed;
+    len -= processed;
+    total_processed += processed;
+    if (process_single_input_frame() || processed == 0) {
+      break;
+    }
+  }
+  return total_processed;
+}
+
+void Http2DecoderAdapter::Reset() {
+  ResetInternal();
+}
+
+Http2DecoderAdapter::SpdyState Http2DecoderAdapter::state() const {
+  return spdy_state_;
+}
+
+Http2DecoderAdapter::SpdyFramerError Http2DecoderAdapter::spdy_framer_error()
+    const {
+  return spdy_framer_error_;
+}
+
+bool Http2DecoderAdapter::probable_http_response() const {
+  return latched_probable_http_response_;
+}
+
+size_t Http2DecoderAdapter::EstimateMemoryUsage() const {
+  // Skip |frame_decoder_|, |frame_header_| and |hpack_first_frame_header_| as
+  // they don't allocate.
+  return SpdyEstimateMemoryUsage(alt_svc_origin_) +
+         SpdyEstimateMemoryUsage(alt_svc_value_);
+}
+
+// ===========================================================================
+// Implementations of the methods declared by Http2FrameDecoderListener.
+
+// Called once the common frame header has been decoded for any frame.
+// This function is largely based on Http2DecoderAdapter::ValidateFrameHeader
+// and some parts of Http2DecoderAdapter::ProcessCommonHeader.
+bool Http2DecoderAdapter::OnFrameHeader(const Http2FrameHeader& header) {
+  DVLOG(1) << "OnFrameHeader: " << header;
+  decoded_frame_header_ = true;
+  if (!latched_probable_http_response_) {
+    latched_probable_http_response_ = header.IsProbableHttpResponse();
+  }
+  const uint8_t raw_frame_type = static_cast<uint8_t>(header.type);
+  visitor()->OnCommonHeader(header.stream_id, header.payload_length,
+                            raw_frame_type, header.flags);
+  if (has_expected_frame_type_ && header.type != expected_frame_type_) {
+    // Report an unexpected frame error and close the connection if we
+    // expect a known frame type (probably CONTINUATION) and receive an
+    // unknown frame.
+    VLOG(1) << "The framer was expecting to receive a " << expected_frame_type_
+            << " frame, but instead received an unknown frame of type "
+            << header.type;
+    SetSpdyErrorAndNotify(SpdyFramerError::SPDY_UNEXPECTED_FRAME);
+    return false;
+  }
+  if (!IsSupportedHttp2FrameType(header.type)) {
+    if (extension_ != nullptr) {
+      // Unknown frames will be passed to the registered extension.
+      return true;
+    }
+    // In HTTP2 we ignore unknown frame types for extensibility, as long as
+    // the rest of the control frame header is valid.
+    // We rely on the visitor to check validity of stream_id.
+    bool valid_stream =
+        visitor()->OnUnknownFrame(header.stream_id, raw_frame_type);
+    if (!valid_stream) {
+      // Report an invalid frame error if the stream_id is not valid.
+      VLOG(1) << "Unknown control frame type " << header.type
+              << " received on invalid stream " << header.stream_id;
+      SetSpdyErrorAndNotify(SpdyFramerError::SPDY_INVALID_CONTROL_FRAME);
+      return false;
+    } else {
+      DVLOG(1) << "Ignoring unknown frame type " << header.type;
+      return true;
+    }
+  }
+
+  SpdyFrameType frame_type = ToSpdyFrameType(header.type);
+  if (!IsValidHTTP2FrameStreamId(header.stream_id, frame_type)) {
+    VLOG(1) << "The framer received an invalid streamID of " << header.stream_id
+            << " for a frame of type " << header.type;
+    SetSpdyErrorAndNotify(SpdyFramerError::SPDY_INVALID_STREAM_ID);
+    return false;
+  }
+
+  if (has_expected_frame_type_ && header.type != expected_frame_type_) {
+    VLOG(1) << "Expected frame type " << expected_frame_type_ << ", not "
+            << header.type;
+    SetSpdyErrorAndNotify(SpdyFramerError::SPDY_UNEXPECTED_FRAME);
+    return false;
+  }
+
+  if (!has_expected_frame_type_ &&
+      header.type == Http2FrameType::CONTINUATION) {
+    VLOG(1) << "Got CONTINUATION frame when not expected.";
+    SetSpdyErrorAndNotify(SpdyFramerError::SPDY_UNEXPECTED_FRAME);
+    return false;
+  }
+
+  if (header.type == Http2FrameType::DATA) {
+    // For some reason SpdyFramer still rejects invalid DATA frame flags.
+    uint8_t valid_flags = Http2FrameFlag::PADDED | Http2FrameFlag::END_STREAM;
+    if (header.HasAnyFlags(~valid_flags)) {
+      SetSpdyErrorAndNotify(SpdyFramerError::SPDY_INVALID_DATA_FRAME_FLAGS);
+      return false;
+    }
+  }
+
+  return true;
+}
+
+void Http2DecoderAdapter::OnDataStart(const Http2FrameHeader& header) {
+  DVLOG(1) << "OnDataStart: " << header;
+
+  if (IsOkToStartFrame(header) && HasRequiredStreamId(header)) {
+    frame_header_ = header;
+    has_frame_header_ = true;
+    visitor()->OnDataFrameHeader(header.stream_id, header.payload_length,
+                                 header.IsEndStream());
+  }
+}
+
+void Http2DecoderAdapter::OnDataPayload(const char* data, size_t len) {
+  DVLOG(1) << "OnDataPayload: len=" << len;
+  DCHECK(has_frame_header_);
+  DCHECK_EQ(frame_header_.type, Http2FrameType::DATA);
+  visitor()->OnStreamFrameData(frame_header().stream_id, data, len);
+}
+
+void Http2DecoderAdapter::OnDataEnd() {
+  DVLOG(1) << "OnDataEnd";
+  DCHECK(has_frame_header_);
+  DCHECK_EQ(frame_header_.type, Http2FrameType::DATA);
+  if (frame_header().IsEndStream()) {
+    visitor()->OnStreamEnd(frame_header().stream_id);
+  }
+  opt_pad_length_.reset();
+}
+
+void Http2DecoderAdapter::OnHeadersStart(const Http2FrameHeader& header) {
+  DVLOG(1) << "OnHeadersStart: " << header;
+  if (IsOkToStartFrame(header) && HasRequiredStreamId(header)) {
+    frame_header_ = header;
+    has_frame_header_ = true;
+    if (header.HasPriority()) {
+      // Once we've got the priority fields, then we can report the arrival
+      // of this HEADERS frame.
+      on_headers_called_ = false;
+      return;
+    }
+    on_headers_called_ = true;
+    ReportReceiveCompressedFrame(header);
+    visitor()->OnHeaders(header.stream_id, kNotHasPriorityFields,
+                         0,      // priority
+                         0,      // parent_stream_id
+                         false,  // exclusive
+                         header.IsEndStream(), header.IsEndHeaders());
+    CommonStartHpackBlock();
+  }
+}
+
+void Http2DecoderAdapter::OnHeadersPriority(
+    const Http2PriorityFields& priority) {
+  DVLOG(1) << "OnHeadersPriority: " << priority;
+  DCHECK(has_frame_header_);
+  DCHECK_EQ(frame_type(), Http2FrameType::HEADERS) << frame_header_;
+  DCHECK(frame_header_.HasPriority());
+  DCHECK(!on_headers_called_);
+  on_headers_called_ = true;
+  ReportReceiveCompressedFrame(frame_header_);
+  visitor()->OnHeaders(frame_header_.stream_id, kHasPriorityFields,
+                       priority.weight, priority.stream_dependency,
+                       priority.is_exclusive, frame_header_.IsEndStream(),
+                       frame_header_.IsEndHeaders());
+  CommonStartHpackBlock();
+}
+
+void Http2DecoderAdapter::OnHpackFragment(const char* data, size_t len) {
+  DVLOG(1) << "OnHpackFragment: len=" << len;
+  on_hpack_fragment_called_ = true;
+  if (!GetHpackDecoder()->HandleControlFrameHeadersData(data, len)) {
+    SetSpdyErrorAndNotify(SpdyFramerError::SPDY_DECOMPRESS_FAILURE);
+    return;
+  }
+}
+
+void Http2DecoderAdapter::OnHeadersEnd() {
+  DVLOG(1) << "OnHeadersEnd";
+  CommonHpackFragmentEnd();
+  opt_pad_length_.reset();
+}
+
+void Http2DecoderAdapter::OnPriorityFrame(const Http2FrameHeader& header,
+                                          const Http2PriorityFields& priority) {
+  DVLOG(1) << "OnPriorityFrame: " << header << "; priority: " << priority;
+  if (IsOkToStartFrame(header) && HasRequiredStreamId(header)) {
+    visitor()->OnPriority(header.stream_id, priority.stream_dependency,
+                          priority.weight, priority.is_exclusive);
+  }
+}
+
+void Http2DecoderAdapter::OnContinuationStart(const Http2FrameHeader& header) {
+  DVLOG(1) << "OnContinuationStart: " << header;
+  if (IsOkToStartFrame(header) && HasRequiredStreamId(header)) {
+    DCHECK(has_hpack_first_frame_header_);
+    if (header.stream_id != hpack_first_frame_header_.stream_id) {
+      SetSpdyErrorAndNotify(SpdyFramerError::SPDY_UNEXPECTED_FRAME);
+      return;
+    }
+    frame_header_ = header;
+    has_frame_header_ = true;
+    ReportReceiveCompressedFrame(header);
+    visitor()->OnContinuation(header.stream_id, header.IsEndHeaders());
+  }
+}
+
+void Http2DecoderAdapter::OnContinuationEnd() {
+  DVLOG(1) << "OnContinuationEnd";
+  CommonHpackFragmentEnd();
+}
+
+void Http2DecoderAdapter::OnPadLength(size_t trailing_length) {
+  DVLOG(1) << "OnPadLength: " << trailing_length;
+  opt_pad_length_ = trailing_length;
+  DCHECK_LT(trailing_length, 256u);
+  if (frame_header_.type == Http2FrameType::DATA) {
+    visitor()->OnStreamPadLength(stream_id(), trailing_length);
+  }
+}
+
+void Http2DecoderAdapter::OnPadding(const char* padding,
+                                    size_t skipped_length) {
+  DVLOG(1) << "OnPadding: " << skipped_length;
+  if (frame_header_.type == Http2FrameType::DATA) {
+    visitor()->OnStreamPadding(stream_id(), skipped_length);
+  } else {
+    MaybeAnnounceEmptyFirstHpackFragment();
+  }
+}
+
+void Http2DecoderAdapter::OnRstStream(const Http2FrameHeader& header,
+                                      Http2ErrorCode http2_error_code) {
+  DVLOG(1) << "OnRstStream: " << header << "; code=" << http2_error_code;
+  if (IsOkToStartFrame(header) && HasRequiredStreamId(header)) {
+    SpdyErrorCode error_code =
+        ParseErrorCode(static_cast<uint32_t>(http2_error_code));
+    visitor()->OnRstStream(header.stream_id, error_code);
+  }
+}
+
+void Http2DecoderAdapter::OnSettingsStart(const Http2FrameHeader& header) {
+  DVLOG(1) << "OnSettingsStart: " << header;
+  if (IsOkToStartFrame(header) && HasRequiredStreamIdZero(header)) {
+    frame_header_ = header;
+    has_frame_header_ = true;
+    visitor()->OnSettings();
+  }
+}
+
+void Http2DecoderAdapter::OnSetting(const Http2SettingFields& setting_fields) {
+  DVLOG(1) << "OnSetting: " << setting_fields;
+  const auto parameter = static_cast<SpdySettingsId>(setting_fields.parameter);
+  visitor()->OnSetting(parameter, setting_fields.value);
+  if (extension_ != nullptr) {
+    extension_->OnSetting(parameter, setting_fields.value);
+  }
+}
+
+void Http2DecoderAdapter::OnSettingsEnd() {
+  DVLOG(1) << "OnSettingsEnd";
+  visitor()->OnSettingsEnd();
+}
+
+void Http2DecoderAdapter::OnSettingsAck(const Http2FrameHeader& header) {
+  DVLOG(1) << "OnSettingsAck: " << header;
+  if (IsOkToStartFrame(header) && HasRequiredStreamIdZero(header)) {
+    visitor()->OnSettingsAck();
+  }
+}
+
+void Http2DecoderAdapter::OnPushPromiseStart(
+    const Http2FrameHeader& header,
+    const Http2PushPromiseFields& promise,
+    size_t total_padding_length) {
+  DVLOG(1) << "OnPushPromiseStart: " << header << "; promise: " << promise
+           << "; total_padding_length: " << total_padding_length;
+  if (IsOkToStartFrame(header) && HasRequiredStreamId(header)) {
+    if (promise.promised_stream_id == 0) {
+      SetSpdyErrorAndNotify(SpdyFramerError::SPDY_INVALID_CONTROL_FRAME);
+      return;
+    }
+    frame_header_ = header;
+    has_frame_header_ = true;
+    ReportReceiveCompressedFrame(header);
+    visitor()->OnPushPromise(header.stream_id, promise.promised_stream_id,
+                             header.IsEndHeaders());
+    CommonStartHpackBlock();
+  }
+}
+
+void Http2DecoderAdapter::OnPushPromiseEnd() {
+  DVLOG(1) << "OnPushPromiseEnd";
+  CommonHpackFragmentEnd();
+  opt_pad_length_.reset();
+}
+
+void Http2DecoderAdapter::OnPing(const Http2FrameHeader& header,
+                                 const Http2PingFields& ping) {
+  DVLOG(1) << "OnPing: " << header << "; ping: " << ping;
+  if (IsOkToStartFrame(header) && HasRequiredStreamIdZero(header)) {
+    visitor()->OnPing(ToSpdyPingId(ping), false);
+  }
+}
+
+void Http2DecoderAdapter::OnPingAck(const Http2FrameHeader& header,
+                                    const Http2PingFields& ping) {
+  DVLOG(1) << "OnPingAck: " << header << "; ping: " << ping;
+  if (IsOkToStartFrame(header) && HasRequiredStreamIdZero(header)) {
+    visitor()->OnPing(ToSpdyPingId(ping), true);
+  }
+}
+
+void Http2DecoderAdapter::OnGoAwayStart(const Http2FrameHeader& header,
+                                        const Http2GoAwayFields& goaway) {
+  DVLOG(1) << "OnGoAwayStart: " << header << "; goaway: " << goaway;
+  if (IsOkToStartFrame(header) && HasRequiredStreamIdZero(header)) {
+    frame_header_ = header;
+    has_frame_header_ = true;
+    SpdyErrorCode error_code =
+        ParseErrorCode(static_cast<uint32_t>(goaway.error_code));
+    visitor()->OnGoAway(goaway.last_stream_id, error_code);
+  }
+}
+
+void Http2DecoderAdapter::OnGoAwayOpaqueData(const char* data, size_t len) {
+  DVLOG(1) << "OnGoAwayOpaqueData: len=" << len;
+  visitor()->OnGoAwayFrameData(data, len);
+}
+
+void Http2DecoderAdapter::OnGoAwayEnd() {
+  DVLOG(1) << "OnGoAwayEnd";
+  visitor()->OnGoAwayFrameData(nullptr, 0);
+}
+
+void Http2DecoderAdapter::OnWindowUpdate(const Http2FrameHeader& header,
+                                         uint32_t increment) {
+  DVLOG(1) << "OnWindowUpdate: " << header << "; increment=" << increment;
+  if (IsOkToStartFrame(header)) {
+    visitor()->OnWindowUpdate(header.stream_id, increment);
+  }
+}
+
+// Per RFC7838, an ALTSVC frame on stream 0 with origin_length == 0, or one on
+// a stream other than stream 0 with origin_length != 0 MUST be ignored.  All
+// frames are decoded by Http2DecoderAdapter, and it is left to the consumer
+// (listener) to implement this behavior.
+void Http2DecoderAdapter::OnAltSvcStart(const Http2FrameHeader& header,
+                                        size_t origin_length,
+                                        size_t value_length) {
+  DVLOG(1) << "OnAltSvcStart: " << header
+           << "; origin_length: " << origin_length
+           << "; value_length: " << value_length;
+  if (!IsOkToStartFrame(header)) {
+    return;
+  }
+  frame_header_ = header;
+  has_frame_header_ = true;
+  alt_svc_origin_.clear();
+  alt_svc_value_.clear();
+}
+
+void Http2DecoderAdapter::OnAltSvcOriginData(const char* data, size_t len) {
+  DVLOG(1) << "OnAltSvcOriginData: len=" << len;
+  alt_svc_origin_.append(data, len);
+}
+
+// Called when decoding the Alt-Svc-Field-Value of an ALTSVC;
+// the field is uninterpreted.
+void Http2DecoderAdapter::OnAltSvcValueData(const char* data, size_t len) {
+  DVLOG(1) << "OnAltSvcValueData: len=" << len;
+  alt_svc_value_.append(data, len);
+}
+
+void Http2DecoderAdapter::OnAltSvcEnd() {
+  DVLOG(1) << "OnAltSvcEnd: origin.size(): " << alt_svc_origin_.size()
+           << "; value.size(): " << alt_svc_value_.size();
+  SpdyAltSvcWireFormat::AlternativeServiceVector altsvc_vector;
+  if (!SpdyAltSvcWireFormat::ParseHeaderFieldValue(alt_svc_value_,
+                                                   &altsvc_vector)) {
+    DLOG(ERROR) << "SpdyAltSvcWireFormat::ParseHeaderFieldValue failed.";
+    SetSpdyErrorAndNotify(SpdyFramerError::SPDY_INVALID_CONTROL_FRAME);
+    return;
+  }
+  visitor()->OnAltSvc(frame_header_.stream_id, alt_svc_origin_, altsvc_vector);
+  // We assume that ALTSVC frames are rare, so get rid of the storage.
+  alt_svc_origin_.clear();
+  alt_svc_origin_.shrink_to_fit();
+  alt_svc_value_.clear();
+  alt_svc_value_.shrink_to_fit();
+}
+
+// Except for BLOCKED frames, all other unknown frames are either dropped or
+// passed to a registered extension.
+void Http2DecoderAdapter::OnUnknownStart(const Http2FrameHeader& header) {
+  DVLOG(1) << "OnUnknownStart: " << header;
+  if (IsOkToStartFrame(header)) {
+    if (extension_ != nullptr) {
+      const uint8_t type = static_cast<uint8_t>(header.type);
+      const uint8_t flags = static_cast<uint8_t>(header.flags);
+      handling_extension_payload_ = extension_->OnFrameHeader(
+          header.stream_id, header.payload_length, type, flags);
+    }
+  }
+}
+
+void Http2DecoderAdapter::OnUnknownPayload(const char* data, size_t len) {
+  if (handling_extension_payload_) {
+    extension_->OnFramePayload(data, len);
+  } else {
+    DVLOG(1) << "OnUnknownPayload: len=" << len;
+  }
+}
+
+void Http2DecoderAdapter::OnUnknownEnd() {
+  DVLOG(1) << "OnUnknownEnd";
+  handling_extension_payload_ = false;
+}
+
+void Http2DecoderAdapter::OnPaddingTooLong(const Http2FrameHeader& header,
+                                           size_t missing_length) {
+  DVLOG(1) << "OnPaddingTooLong: " << header
+           << "; missing_length: " << missing_length;
+  if (header.type == Http2FrameType::DATA) {
+    if (header.payload_length == 0) {
+      DCHECK_EQ(1u, missing_length);
+      SetSpdyErrorAndNotify(SpdyFramerError::SPDY_INVALID_DATA_FRAME_FLAGS);
+      return;
+    }
+    visitor()->OnStreamPadding(header.stream_id, 1);
+  }
+  SetSpdyErrorAndNotify(SpdyFramerError::SPDY_INVALID_PADDING);
+}
+
+void Http2DecoderAdapter::OnFrameSizeError(const Http2FrameHeader& header) {
+  DVLOG(1) << "OnFrameSizeError: " << header;
+  size_t recv_limit = recv_frame_size_limit_;
+  if (header.payload_length > recv_limit) {
+    SetSpdyErrorAndNotify(SpdyFramerError::SPDY_OVERSIZED_PAYLOAD);
+    return;
+  }
+  if (header.type != Http2FrameType::DATA &&
+      header.payload_length > recv_limit) {
+    SetSpdyErrorAndNotify(SpdyFramerError::SPDY_CONTROL_PAYLOAD_TOO_LARGE);
+    return;
+  }
+  switch (header.type) {
+    case Http2FrameType::GOAWAY:
+    case Http2FrameType::ALTSVC:
+      SetSpdyErrorAndNotify(SpdyFramerError::SPDY_INVALID_CONTROL_FRAME);
+      break;
+    default:
+      SetSpdyErrorAndNotify(SpdyFramerError::SPDY_INVALID_CONTROL_FRAME_SIZE);
+  }
+}
+
+// Decodes the input up to the next frame boundary (i.e. at most one frame),
+// stopping early if an error is detected.
+size_t Http2DecoderAdapter::ProcessInputFrame(const char* data, size_t len) {
+  DCHECK_NE(spdy_state_, SpdyState::SPDY_ERROR);
+  DecodeBuffer db(data, len);
+  DecodeStatus status = frame_decoder_->DecodeFrame(&db);
+  if (spdy_state_ != SpdyState::SPDY_ERROR) {
+    DetermineSpdyState(status);
+  } else {
+    VLOG(1) << "ProcessInputFrame spdy_framer_error_="
+            << SpdyFramerErrorToString(spdy_framer_error_);
+    if (spdy_framer_error_ == SpdyFramerError::SPDY_INVALID_PADDING &&
+        has_frame_header_ && frame_type() != Http2FrameType::DATA) {
+      // spdy_framer_test checks that all of the available frame payload
+      // has been consumed, so do that.
+      size_t total = remaining_total_payload();
+      if (total <= frame_header().payload_length) {
+        size_t avail = db.MinLengthRemaining(total);
+        VLOG(1) << "Skipping past " << avail << " bytes, of " << total
+                << " total remaining in the frame's payload.";
+        db.AdvanceCursor(avail);
+      } else {
+        SPDY_BUG << "Total remaining (" << total
+                 << ") should not be greater than the payload length; "
+                 << frame_header();
+      }
+    }
+  }
+  return db.Offset();
+}
+
+// After decoding, determine the next SpdyState. Only called if the current
+// state is NOT SpdyState::SPDY_ERROR (i.e. if none of the callback methods
+// detected an error condition), because otherwise we assume that the callback
+// method has set spdy_framer_error_ appropriately.
+void Http2DecoderAdapter::DetermineSpdyState(DecodeStatus status) {
+  DCHECK_EQ(spdy_framer_error_, SPDY_NO_ERROR);
+  DCHECK(!HasError()) << spdy_framer_error_;
+  switch (status) {
+    case DecodeStatus::kDecodeDone:
+      DVLOG(1) << "ProcessInputFrame -> DecodeStatus::kDecodeDone";
+      ResetBetweenFrames();
+      break;
+    case DecodeStatus::kDecodeInProgress:
+      DVLOG(1) << "ProcessInputFrame -> DecodeStatus::kDecodeInProgress";
+      if (decoded_frame_header_) {
+        if (IsDiscardingPayload()) {
+          set_spdy_state(SpdyState::SPDY_IGNORE_REMAINING_PAYLOAD);
+        } else if (has_frame_header_ && frame_type() == Http2FrameType::DATA) {
+          if (IsReadingPaddingLength()) {
+            set_spdy_state(SpdyState::SPDY_READ_DATA_FRAME_PADDING_LENGTH);
+          } else if (IsSkippingPadding()) {
+            set_spdy_state(SpdyState::SPDY_CONSUME_PADDING);
+          } else {
+            set_spdy_state(SpdyState::SPDY_FORWARD_STREAM_FRAME);
+          }
+        } else {
+          set_spdy_state(SpdyState::SPDY_CONTROL_FRAME_PAYLOAD);
+        }
+      } else {
+        set_spdy_state(SpdyState::SPDY_READING_COMMON_HEADER);
+      }
+      break;
+    case DecodeStatus::kDecodeError:
+      VLOG(1) << "ProcessInputFrame -> DecodeStatus::kDecodeError";
+      if (IsDiscardingPayload()) {
+        if (remaining_total_payload() == 0) {
+          // Push the Http2FrameDecoder out of state kDiscardPayload now
+          // since doing so requires no input.
+          DecodeBuffer tmp("", 0);
+          DecodeStatus status = frame_decoder_->DecodeFrame(&tmp);
+          if (status != DecodeStatus::kDecodeDone) {
+            SPDY_BUG << "Expected to be done decoding the frame, not "
+                     << status;
+            SetSpdyErrorAndNotify(SPDY_INTERNAL_FRAMER_ERROR);
+          } else if (spdy_framer_error_ != SPDY_NO_ERROR) {
+            SPDY_BUG << "Expected to have no error, not "
+                     << SpdyFramerErrorToString(spdy_framer_error_);
+          } else {
+            ResetBetweenFrames();
+          }
+        } else {
+          set_spdy_state(SpdyState::SPDY_IGNORE_REMAINING_PAYLOAD);
+        }
+      } else {
+        SetSpdyErrorAndNotify(SPDY_INVALID_CONTROL_FRAME);
+      }
+      break;
+  }
+}
+
+void Http2DecoderAdapter::ResetBetweenFrames() {
+  CorruptFrameHeader(&frame_header_);
+  decoded_frame_header_ = false;
+  has_frame_header_ = false;
+  set_spdy_state(SpdyState::SPDY_READY_FOR_FRAME);
+}
+
+// ResetInternal is called from the constructor, and during tests, but not
+// otherwise (i.e. not between every frame).
+void Http2DecoderAdapter::ResetInternal() {
+  set_spdy_state(SpdyState::SPDY_READY_FOR_FRAME);
+  spdy_framer_error_ = SpdyFramerError::SPDY_NO_ERROR;
+
+  decoded_frame_header_ = false;
+  has_frame_header_ = false;
+  on_headers_called_ = false;
+  on_hpack_fragment_called_ = false;
+  latched_probable_http_response_ = false;
+  has_expected_frame_type_ = false;
+
+  CorruptFrameHeader(&frame_header_);
+  CorruptFrameHeader(&hpack_first_frame_header_);
+
+  frame_decoder_ = SpdyMakeUnique<Http2FrameDecoder>(this);
+  hpack_decoder_ = nullptr;
+}
+
+void Http2DecoderAdapter::set_spdy_state(SpdyState v) {
+  DVLOG(2) << "set_spdy_state(" << StateToString(v) << ")";
+  spdy_state_ = v;
+}
+
+void Http2DecoderAdapter::SetSpdyErrorAndNotify(SpdyFramerError error) {
+  if (HasError()) {
+    DCHECK_EQ(spdy_state_, SpdyState::SPDY_ERROR);
+  } else {
+    VLOG(2) << "SetSpdyErrorAndNotify(" << SpdyFramerErrorToString(error)
+            << ")";
+    DCHECK_NE(error, SpdyFramerError::SPDY_NO_ERROR);
+    spdy_framer_error_ = error;
+    set_spdy_state(SpdyState::SPDY_ERROR);
+    frame_decoder_->set_listener(&no_op_listener_);
+    visitor()->OnError(error);
+  }
+}
+
+bool Http2DecoderAdapter::HasError() const {
+  if (spdy_state_ == SpdyState::SPDY_ERROR) {
+    DCHECK_NE(spdy_framer_error(), SpdyFramerError::SPDY_NO_ERROR);
+    return true;
+  } else {
+    DCHECK_EQ(spdy_framer_error(), SpdyFramerError::SPDY_NO_ERROR);
+    return false;
+  }
+}
+
+const Http2FrameHeader& Http2DecoderAdapter::frame_header() const {
+  DCHECK(has_frame_header_);
+  return frame_header_;
+}
+
+uint32_t Http2DecoderAdapter::stream_id() const {
+  return frame_header().stream_id;
+}
+
+Http2FrameType Http2DecoderAdapter::frame_type() const {
+  return frame_header().type;
+}
+
+size_t Http2DecoderAdapter::remaining_total_payload() const {
+  DCHECK(has_frame_header_);
+  size_t remaining = frame_decoder_->remaining_payload();
+  if (IsPaddable(frame_type()) && frame_header_.IsPadded()) {
+    remaining += frame_decoder_->remaining_padding();
+  }
+  return remaining;
+}
+
+bool Http2DecoderAdapter::IsReadingPaddingLength() {
+  bool result = frame_header_.IsPadded() && !opt_pad_length_;
+  DVLOG(2) << "Http2DecoderAdapter::IsReadingPaddingLength: " << result;
+  return result;
+}
+bool Http2DecoderAdapter::IsSkippingPadding() {
+  bool result = frame_header_.IsPadded() && opt_pad_length_ &&
+                frame_decoder_->remaining_payload() == 0 &&
+                frame_decoder_->remaining_padding() > 0;
+  DVLOG(2) << "Http2DecoderAdapter::IsSkippingPadding: " << result;
+  return result;
+}
+bool Http2DecoderAdapter::IsDiscardingPayload() {
+  bool result = decoded_frame_header_ && frame_decoder_->IsDiscardingPayload();
+  DVLOG(2) << "Http2DecoderAdapter::IsDiscardingPayload: " << result;
+  return result;
+}
+// Called from OnXyz or OnXyzStart methods to decide whether it is OK to
+// handle the callback.
+bool Http2DecoderAdapter::IsOkToStartFrame(const Http2FrameHeader& header) {
+  DVLOG(3) << "IsOkToStartFrame";
+  if (HasError()) {
+    VLOG(2) << "HasError()";
+    return false;
+  }
+  DCHECK(!has_frame_header_);
+  if (has_expected_frame_type_ && header.type != expected_frame_type_) {
+    VLOG(1) << "Expected frame type " << expected_frame_type_ << ", not "
+            << header.type;
+    SetSpdyErrorAndNotify(SpdyFramerError::SPDY_UNEXPECTED_FRAME);
+    return false;
+  }
+
+  return true;
+}
+
+bool Http2DecoderAdapter::HasRequiredStreamId(uint32_t stream_id) {
+  DVLOG(3) << "HasRequiredStreamId: " << stream_id;
+  if (HasError()) {
+    VLOG(2) << "HasError()";
+    return false;
+  }
+  if (stream_id != 0) {
+    return true;
+  }
+  VLOG(1) << "Stream Id is required, but zero provided";
+  SetSpdyErrorAndNotify(SpdyFramerError::SPDY_INVALID_STREAM_ID);
+  return false;
+}
+
+bool Http2DecoderAdapter::HasRequiredStreamId(const Http2FrameHeader& header) {
+  return HasRequiredStreamId(header.stream_id);
+}
+
+bool Http2DecoderAdapter::HasRequiredStreamIdZero(uint32_t stream_id) {
+  DVLOG(3) << "HasRequiredStreamIdZero: " << stream_id;
+  if (HasError()) {
+    VLOG(2) << "HasError()";
+    return false;
+  }
+  if (stream_id == 0) {
+    return true;
+  }
+  VLOG(1) << "Stream Id was not zero, as required: " << stream_id;
+  SetSpdyErrorAndNotify(SpdyFramerError::SPDY_INVALID_STREAM_ID);
+  return false;
+}
+
+bool Http2DecoderAdapter::HasRequiredStreamIdZero(
+    const Http2FrameHeader& header) {
+  return HasRequiredStreamIdZero(header.stream_id);
+}
+
+void Http2DecoderAdapter::ReportReceiveCompressedFrame(
+    const Http2FrameHeader& header) {
+  if (debug_visitor() != nullptr) {
+    size_t total = header.payload_length + Http2FrameHeader::EncodedSize();
+    debug_visitor()->OnReceiveCompressedFrame(
+        header.stream_id, ToSpdyFrameType(header.type), total);
+  }
+}
+
+HpackDecoderAdapter* Http2DecoderAdapter::GetHpackDecoder() {
+  if (hpack_decoder_ == nullptr) {
+    hpack_decoder_ = SpdyMakeUnique<HpackDecoderAdapter>();
+  }
+  return hpack_decoder_.get();
+}
+
+void Http2DecoderAdapter::CommonStartHpackBlock() {
+  DVLOG(1) << "CommonStartHpackBlock";
+  DCHECK(!has_hpack_first_frame_header_);
+  if (!frame_header_.IsEndHeaders()) {
+    hpack_first_frame_header_ = frame_header_;
+    has_hpack_first_frame_header_ = true;
+  } else {
+    CorruptFrameHeader(&hpack_first_frame_header_);
+  }
+  on_hpack_fragment_called_ = false;
+  SpdyHeadersHandlerInterface* handler =
+      visitor()->OnHeaderFrameStart(stream_id());
+  if (handler == nullptr) {
+    SPDY_BUG << "visitor_->OnHeaderFrameStart returned nullptr";
+    SetSpdyErrorAndNotify(SpdyFramerError::SPDY_INTERNAL_FRAMER_ERROR);
+    return;
+  }
+  GetHpackDecoder()->HandleControlFrameHeadersStart(handler);
+}
+
+// SpdyFramer calls HandleControlFrameHeadersData even if there are zero
+// fragment bytes in the first frame, so do the same.
+void Http2DecoderAdapter::MaybeAnnounceEmptyFirstHpackFragment() {
+  if (!on_hpack_fragment_called_) {
+    OnHpackFragment(nullptr, 0);
+    DCHECK(on_hpack_fragment_called_);
+  }
+}
+
+void Http2DecoderAdapter::CommonHpackFragmentEnd() {
+  DVLOG(1) << "CommonHpackFragmentEnd: stream_id=" << stream_id();
+  if (HasError()) {
+    VLOG(1) << "HasError(), returning";
+    return;
+  }
+  DCHECK(has_frame_header_);
+  MaybeAnnounceEmptyFirstHpackFragment();
+  if (frame_header_.IsEndHeaders()) {
+    DCHECK_EQ(has_hpack_first_frame_header_,
+              frame_type() == Http2FrameType::CONTINUATION)
+        << frame_header();
+    has_expected_frame_type_ = false;
+    if (GetHpackDecoder()->HandleControlFrameHeadersComplete(nullptr)) {
+      visitor()->OnHeaderFrameEnd(stream_id());
+    } else {
+      SetSpdyErrorAndNotify(SpdyFramerError::SPDY_DECOMPRESS_FAILURE);
+      return;
+    }
+    const Http2FrameHeader& first = frame_type() == Http2FrameType::CONTINUATION
+                                        ? hpack_first_frame_header_
+                                        : frame_header_;
+    if (first.type == Http2FrameType::HEADERS && first.IsEndStream()) {
+      visitor()->OnStreamEnd(first.stream_id);
+    }
+    has_hpack_first_frame_header_ = false;
+    CorruptFrameHeader(&hpack_first_frame_header_);
+  } else {
+    DCHECK(has_hpack_first_frame_header_);
+    has_expected_frame_type_ = true;
+    expected_frame_type_ = Http2FrameType::CONTINUATION;
+  }
+}
+
+}  // namespace http2
+
+namespace spdy {
+
+bool SpdyFramerVisitorInterface::OnGoAwayFrameData(const char* goaway_data,
+                                                   size_t len) {
+  return true;
+}
+
+}  // namespace spdy
diff --git a/spdy/core/http2_frame_decoder_adapter.h b/spdy/core/http2_frame_decoder_adapter.h
new file mode 100644
index 0000000..02deafd
--- /dev/null
+++ b/spdy/core/http2_frame_decoder_adapter.h
@@ -0,0 +1,514 @@
+// Copyright 2016 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef QUICHE_SPDY_CORE_HTTP2_FRAME_DECODER_ADAPTER_H_
+#define QUICHE_SPDY_CORE_HTTP2_FRAME_DECODER_ADAPTER_H_
+
+#include <stddef.h>
+
+#include <cstdint>
+#include <memory>
+
+#include "net/third_party/quiche/src/http2/decoder/http2_frame_decoder.h"
+#include "net/third_party/quiche/src/http2/platform/api/http2_optional.h"
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_decoder_adapter.h"
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_header_table.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_alt_svc_wire_format.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_headers_handler_interface.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_protocol.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string_piece.h"
+
+namespace spdy {
+
+class SpdyFramerVisitorInterface;
+class ExtensionVisitorInterface;
+
+}  // namespace spdy
+
+// TODO(dahollings): Perform various renames/moves suggested in cl/164660364.
+
+namespace http2 {
+
+// Adapts SpdyFramer interface to use Http2FrameDecoder.
+class SPDY_EXPORT_PRIVATE Http2DecoderAdapter
+    : public http2::Http2FrameDecoderListener {
+ public:
+  // HTTP2 states.
+  enum SpdyState {
+    SPDY_ERROR,
+    SPDY_READY_FOR_FRAME,  // Framer is ready for reading the next frame.
+    SPDY_FRAME_COMPLETE,  // Framer has finished reading a frame, need to reset.
+    SPDY_READING_COMMON_HEADER,
+    SPDY_CONTROL_FRAME_PAYLOAD,
+    SPDY_READ_DATA_FRAME_PADDING_LENGTH,
+    SPDY_CONSUME_PADDING,
+    SPDY_IGNORE_REMAINING_PAYLOAD,
+    SPDY_FORWARD_STREAM_FRAME,
+    SPDY_CONTROL_FRAME_BEFORE_HEADER_BLOCK,
+    SPDY_CONTROL_FRAME_HEADER_BLOCK,
+    SPDY_GOAWAY_FRAME_PAYLOAD,
+    SPDY_SETTINGS_FRAME_HEADER,
+    SPDY_SETTINGS_FRAME_PAYLOAD,
+    SPDY_ALTSVC_FRAME_PAYLOAD,
+    SPDY_EXTENSION_FRAME_PAYLOAD,
+  };
+
+  // Framer error codes.
+  enum SpdyFramerError {
+    SPDY_NO_ERROR,
+    SPDY_INVALID_STREAM_ID,            // Stream ID is invalid
+    SPDY_INVALID_CONTROL_FRAME,        // Control frame is mal-formatted.
+    SPDY_CONTROL_PAYLOAD_TOO_LARGE,    // Control frame payload was too large.
+    SPDY_ZLIB_INIT_FAILURE,            // The Zlib library could not initialize.
+    SPDY_UNSUPPORTED_VERSION,          // Control frame has unsupported version.
+    SPDY_DECOMPRESS_FAILURE,           // There was an error decompressing.
+    SPDY_COMPRESS_FAILURE,             // There was an error compressing.
+    SPDY_GOAWAY_FRAME_CORRUPT,         // GOAWAY frame could not be parsed.
+    SPDY_RST_STREAM_FRAME_CORRUPT,     // RST_STREAM frame could not be parsed.
+    SPDY_INVALID_PADDING,              // HEADERS or DATA frame padding invalid
+    SPDY_INVALID_DATA_FRAME_FLAGS,     // Data frame has invalid flags.
+    SPDY_INVALID_CONTROL_FRAME_FLAGS,  // Control frame has invalid flags.
+    SPDY_UNEXPECTED_FRAME,             // Frame received out of order.
+    SPDY_INTERNAL_FRAMER_ERROR,        // SpdyFramer was used incorrectly.
+    SPDY_INVALID_CONTROL_FRAME_SIZE,   // Control frame not sized to spec
+    SPDY_OVERSIZED_PAYLOAD,            // Payload size was too large
+
+    LAST_ERROR,  // Must be the last entry in the enum.
+  };
+
+  // For debugging.
+  static const char* StateToString(int state);
+  static const char* SpdyFramerErrorToString(SpdyFramerError spdy_framer_error);
+
+  Http2DecoderAdapter();
+  ~Http2DecoderAdapter() override;
+
+  // Set callbacks to be called from the framer.  A visitor must be set, or
+  // else the framer will likely crash.  It is acceptable for the visitor
+  // to do nothing.  If this is called multiple times, only the last visitor
+  // will be used.
+  void set_visitor(spdy::SpdyFramerVisitorInterface* visitor);
+  spdy::SpdyFramerVisitorInterface* visitor() const { return visitor_; }
+
+  // Set extension callbacks to be called from the framer or decoder. Optional.
+  // If called multiple times, only the last visitor will be used.
+  void set_extension_visitor(spdy::ExtensionVisitorInterface* visitor);
+
+  // Set debug callbacks to be called from the framer. The debug visitor is
+  // completely optional and need not be set in order for normal operation.
+  // If this is called multiple times, only the last visitor will be used.
+  void set_debug_visitor(spdy::SpdyFramerDebugVisitorInterface* debug_visitor);
+  spdy::SpdyFramerDebugVisitorInterface* debug_visitor() const {
+    return debug_visitor_;
+  }
+
+  // Set debug callbacks to be called from the HPACK decoder.
+  void SetDecoderHeaderTableDebugVisitor(
+      std::unique_ptr<spdy::HpackHeaderTable::DebugVisitorInterface> visitor);
+
+  // Sets whether or not ProcessInput returns after finishing a frame, or
+  // continues processing additional frames. Normally ProcessInput processes
+  // all input, but this method enables the caller (and visitor) to work with
+  // a single frame at a time (or that portion of the frame which is provided
+  // as input). Reset() does not change the value of this flag.
+  void set_process_single_input_frame(bool v);
+  bool process_single_input_frame() const {
+    return process_single_input_frame_;
+  }
+
+  // Decode the |len| bytes of encoded HTTP/2 starting at |*data|. Returns
+  // the number of bytes consumed. It is safe to pass more bytes in than
+  // may be consumed. Should process (or otherwise buffer) as much as
+  // available, unless process_single_input_frame is true.
+  size_t ProcessInput(const char* data, size_t len);
+
+  // Reset the decoder (used just for tests at this time).
+  void Reset();
+
+  // Current state of the decoder.
+  SpdyState state() const;
+
+  // Current error code (NO_ERROR if state != ERROR).
+  SpdyFramerError spdy_framer_error() const;
+
+  // Has any frame header looked like the start of an HTTP/1.1 (or earlier)
+  // response? Used to detect if a backend/server that we sent a request to
+  // has responded with an HTTP/1.1 (or earlier) response.
+  bool probable_http_response() const;
+
+  // Returns the estimate of dynamically allocated memory in bytes.
+  size_t EstimateMemoryUsage() const;
+
+  spdy::HpackDecoderAdapter* GetHpackDecoder();
+
+  bool HasError() const;
+
+ private:
+  bool OnFrameHeader(const Http2FrameHeader& header) override;
+  void OnDataStart(const Http2FrameHeader& header) override;
+  void OnDataPayload(const char* data, size_t len) override;
+  void OnDataEnd() override;
+  void OnHeadersStart(const Http2FrameHeader& header) override;
+  void OnHeadersPriority(const Http2PriorityFields& priority) override;
+  void OnHpackFragment(const char* data, size_t len) override;
+  void OnHeadersEnd() override;
+  void OnPriorityFrame(const Http2FrameHeader& header,
+                       const Http2PriorityFields& priority) override;
+  void OnContinuationStart(const Http2FrameHeader& header) override;
+  void OnContinuationEnd() override;
+  void OnPadLength(size_t trailing_length) override;
+  void OnPadding(const char* padding, size_t skipped_length) override;
+  void OnRstStream(const Http2FrameHeader& header,
+                   Http2ErrorCode http2_error_code) override;
+  void OnSettingsStart(const Http2FrameHeader& header) override;
+  void OnSetting(const Http2SettingFields& setting_fields) override;
+  void OnSettingsEnd() override;
+  void OnSettingsAck(const Http2FrameHeader& header) override;
+  void OnPushPromiseStart(const Http2FrameHeader& header,
+                          const Http2PushPromiseFields& promise,
+                          size_t total_padding_length) override;
+  void OnPushPromiseEnd() override;
+  void OnPing(const Http2FrameHeader& header,
+              const Http2PingFields& ping) override;
+  void OnPingAck(const Http2FrameHeader& header,
+                 const Http2PingFields& ping) override;
+  void OnGoAwayStart(const Http2FrameHeader& header,
+                     const Http2GoAwayFields& goaway) override;
+  void OnGoAwayOpaqueData(const char* data, size_t len) override;
+  void OnGoAwayEnd() override;
+  void OnWindowUpdate(const Http2FrameHeader& header,
+                      uint32_t increment) override;
+  void OnAltSvcStart(const Http2FrameHeader& header,
+                     size_t origin_length,
+                     size_t value_length) override;
+  void OnAltSvcOriginData(const char* data, size_t len) override;
+  void OnAltSvcValueData(const char* data, size_t len) override;
+  void OnAltSvcEnd() override;
+  void OnUnknownStart(const Http2FrameHeader& header) override;
+  void OnUnknownPayload(const char* data, size_t len) override;
+  void OnUnknownEnd() override;
+  void OnPaddingTooLong(const Http2FrameHeader& header,
+                        size_t missing_length) override;
+  void OnFrameSizeError(const Http2FrameHeader& header) override;
+
+  size_t ProcessInputFrame(const char* data, size_t len);
+
+  void DetermineSpdyState(DecodeStatus status);
+  void ResetBetweenFrames();
+
+  // ResetInternal is called from the constructor, and during tests, but not
+  // otherwise (i.e. not between every frame).
+  void ResetInternal();
+
+  void set_spdy_state(SpdyState v);
+
+  void SetSpdyErrorAndNotify(SpdyFramerError error);
+
+  const Http2FrameHeader& frame_header() const;
+
+  uint32_t stream_id() const;
+  Http2FrameType frame_type() const;
+
+  size_t remaining_total_payload() const;
+
+  bool IsReadingPaddingLength();
+  bool IsSkippingPadding();
+  bool IsDiscardingPayload();
+  // Called from OnXyz or OnXyzStart methods to decide whether it is OK to
+  // handle the callback.
+  bool IsOkToStartFrame(const Http2FrameHeader& header);
+  bool HasRequiredStreamId(uint32_t stream_id);
+
+  bool HasRequiredStreamId(const Http2FrameHeader& header);
+
+  bool HasRequiredStreamIdZero(uint32_t stream_id);
+
+  bool HasRequiredStreamIdZero(const Http2FrameHeader& header);
+
+  void ReportReceiveCompressedFrame(const Http2FrameHeader& header);
+
+  void CommonStartHpackBlock();
+
+  // SpdyFramer calls HandleControlFrameHeadersData even if there are zero
+  // fragment bytes in the first frame, so do the same.
+  void MaybeAnnounceEmptyFirstHpackFragment();
+  void CommonHpackFragmentEnd();
+
+  // The most recently decoded frame header; invalid after we reached the end
+  // of that frame.
+  Http2FrameHeader frame_header_;
+
+  // If decoding an HPACK block that is split across multiple frames, this holds
+  // the frame header of the HEADERS or PUSH_PROMISE that started the block.
+  Http2FrameHeader hpack_first_frame_header_;
+
+  // Amount of trailing padding. Currently used just as an indicator of whether
+  // OnPadLength has been called.
+  Http2Optional<size_t> opt_pad_length_;
+
+  // Temporary buffers for the AltSvc fields.
+  Http2String alt_svc_origin_;
+  Http2String alt_svc_value_;
+
+  // Listener used if we transition to an error state; the listener ignores all
+  // the callbacks.
+  Http2FrameDecoderNoOpListener no_op_listener_;
+
+  spdy::SpdyFramerVisitorInterface* visitor_ = nullptr;
+  spdy::SpdyFramerDebugVisitorInterface* debug_visitor_ = nullptr;
+
+  // If non-null, unknown frames and settings are passed to the extension.
+  spdy::ExtensionVisitorInterface* extension_ = nullptr;
+
+  // The HPACK decoder to be used for this adapter. User is responsible for
+  // clearing if the adapter is to be used for another connection.
+  std::unique_ptr<spdy::HpackDecoderAdapter> hpack_decoder_ = nullptr;
+
+  // The HTTP/2 frame decoder. Accessed via a unique_ptr to allow replacement
+  // (e.g. in tests) when Reset() is called.
+  std::unique_ptr<Http2FrameDecoder> frame_decoder_;
+
+  // Next frame type expected. Currently only used for CONTINUATION frames,
+  // but could be used for detecting whether the first frame is a SETTINGS
+  // frame.
+  // TODO(jamessyng): Provide means to indicate that decoder should require
+  // SETTINGS frame as the first frame.
+  Http2FrameType expected_frame_type_;
+
+  // Attempt to duplicate the SpdyState and SpdyFramerError values that
+  // SpdyFramer sets. Values determined by getting tests to pass.
+  SpdyState spdy_state_;
+  SpdyFramerError spdy_framer_error_;
+
+  // The limit on the size of received HTTP/2 payloads as specified in the
+  // SETTINGS_MAX_FRAME_SIZE advertised to peer.
+  size_t recv_frame_size_limit_ = spdy::kHttp2DefaultFramePayloadLimit;
+
+  // Has OnFrameHeader been called?
+  bool decoded_frame_header_ = false;
+
+  // Have we recorded an Http2FrameHeader for the current frame?
+  // We only do so if the decoder will make multiple callbacks for
+  // the frame; for example, for PING frames we don't make record
+  // the frame header, but for ALTSVC we do.
+  bool has_frame_header_ = false;
+
+  // Have we recorded an Http2FrameHeader for the current HPACK block?
+  // True only for multi-frame HPACK blocks.
+  bool has_hpack_first_frame_header_ = false;
+
+  // Has OnHeaders() already been called for current HEADERS block? Only
+  // meaningful between OnHeadersStart and OnHeadersPriority.
+  bool on_headers_called_;
+
+  // Has OnHpackFragment() already been called for current HPACK block?
+  // SpdyFramer will pass an empty buffer to the HPACK decoder if a HEADERS
+  // or PUSH_PROMISE has no HPACK data in it (e.g. a HEADERS frame with only
+  // padding). Detect that condition and replicate the behavior using this
+  // field.
+  bool on_hpack_fragment_called_;
+
+  // Have we seen a frame header that appears to be an HTTP/1 response?
+  bool latched_probable_http_response_ = false;
+
+  // Is expected_frame_type_ set?
+  bool has_expected_frame_type_ = false;
+
+  // Is the current frame payload destined for |extension_|?
+  bool handling_extension_payload_ = false;
+
+  bool process_single_input_frame_ = false;
+};
+
+}  // namespace http2
+
+namespace spdy {
+
+// Http2DecoderAdapter will use the given visitor implementing this
+// interface to deliver event callbacks as frames are decoded.
+//
+// Control frames that contain HTTP2 header blocks (HEADER, and PUSH_PROMISE)
+// are processed in fashion that allows the decompressed header block to be
+// delivered in chunks to the visitor.
+// The following steps are followed:
+//   1. OnHeaders, or OnPushPromise is called.
+//   2. OnHeaderFrameStart is called; visitor is expected to return an instance
+//      of SpdyHeadersHandlerInterface that will receive the header key-value
+//      pairs.
+//   3. OnHeaderFrameEnd is called, indicating that the full header block has
+//      been delivered for the control frame.
+// During step 2, if the visitor is not interested in accepting the header data,
+// it should return a no-op implementation of SpdyHeadersHandlerInterface.
+class SPDY_EXPORT_PRIVATE SpdyFramerVisitorInterface {
+ public:
+  virtual ~SpdyFramerVisitorInterface() {}
+
+  // Called if an error is detected in the SpdyFrame protocol.
+  virtual void OnError(http2::Http2DecoderAdapter::SpdyFramerError error) = 0;
+
+  // Called when the common header for a frame is received. Validating the
+  // common header occurs in later processing.
+  virtual void OnCommonHeader(SpdyStreamId /*stream_id*/,
+                              size_t /*length*/,
+                              uint8_t /*type*/,
+                              uint8_t /*flags*/) {}
+
+  // Called when a data frame header is received. The frame's data
+  // payload will be provided via subsequent calls to
+  // OnStreamFrameData().
+  virtual void OnDataFrameHeader(SpdyStreamId stream_id,
+                                 size_t length,
+                                 bool fin) = 0;
+
+  // Called when data is received.
+  // |stream_id| The stream receiving data.
+  // |data| A buffer containing the data received.
+  // |len| The length of the data buffer.
+  virtual void OnStreamFrameData(SpdyStreamId stream_id,
+                                 const char* data,
+                                 size_t len) = 0;
+
+  // Called when the other side has finished sending data on this stream.
+  // |stream_id| The stream that was receiving data.
+  virtual void OnStreamEnd(SpdyStreamId stream_id) = 0;
+
+  // Called when padding length field is received on a DATA frame.
+  // |stream_id| The stream receiving data.
+  // |value| The value of the padding length field.
+  virtual void OnStreamPadLength(SpdyStreamId stream_id, size_t value) {}
+
+  // Called when padding is received (the trailing octets, not pad_len field) on
+  // a DATA frame.
+  // |stream_id| The stream receiving data.
+  // |len| The number of padding octets.
+  virtual void OnStreamPadding(SpdyStreamId stream_id, size_t len) = 0;
+
+  // Called just before processing the payload of a frame containing header
+  // data. Should return an implementation of SpdyHeadersHandlerInterface that
+  // will receive headers for stream |stream_id|. The caller will not take
+  // ownership of the headers handler. The same instance should remain live
+  // and be returned for all header frames comprising a logical header block
+  // (i.e. until OnHeaderFrameEnd() is called).
+  virtual SpdyHeadersHandlerInterface* OnHeaderFrameStart(
+      SpdyStreamId stream_id) = 0;
+
+  // Called after processing the payload of a frame containing header data.
+  virtual void OnHeaderFrameEnd(SpdyStreamId stream_id) = 0;
+
+  // Called when a RST_STREAM frame has been parsed.
+  virtual void OnRstStream(SpdyStreamId stream_id,
+                           SpdyErrorCode error_code) = 0;
+
+  // Called when a SETTINGS frame is received.
+  virtual void OnSettings() {}
+
+  // Called when a complete setting within a SETTINGS frame has been parsed.
+  // Note that |id| may or may not be a SETTINGS ID defined in the HTTP/2 spec.
+  virtual void OnSetting(SpdySettingsId id, uint32_t value) = 0;
+
+  // Called when a SETTINGS frame is received with the ACK flag set.
+  virtual void OnSettingsAck() {}
+
+  // Called before and after parsing SETTINGS id and value tuples.
+  virtual void OnSettingsEnd() = 0;
+
+  // Called when a PING frame has been parsed.
+  virtual void OnPing(SpdyPingId unique_id, bool is_ack) = 0;
+
+  // Called when a GOAWAY frame has been parsed.
+  virtual void OnGoAway(SpdyStreamId last_accepted_stream_id,
+                        SpdyErrorCode error_code) = 0;
+
+  // Called when a HEADERS frame is received.
+  // Note that header block data is not included. See OnHeaderFrameStart().
+  // |stream_id| The stream receiving the header.
+  // |has_priority| Whether or not the headers frame included a priority value,
+  //     and stream dependency info.
+  // |weight| If |has_priority| is true, then weight (in the range [1, 256])
+  //     for the receiving stream, otherwise 0.
+  // |parent_stream_id| If |has_priority| is true the parent stream of the
+  //     receiving stream, else 0.
+  // |exclusive| If |has_priority| is true the exclusivity of dependence on the
+  //     parent stream, else false.
+  // |fin| Whether FIN flag is set in frame headers.
+  // |end| False if HEADERs frame is to be followed by a CONTINUATION frame,
+  //     or true if not.
+  virtual void OnHeaders(SpdyStreamId stream_id,
+                         bool has_priority,
+                         int weight,
+                         SpdyStreamId parent_stream_id,
+                         bool exclusive,
+                         bool fin,
+                         bool end) = 0;
+
+  // Called when a WINDOW_UPDATE frame has been parsed.
+  virtual void OnWindowUpdate(SpdyStreamId stream_id,
+                              int delta_window_size) = 0;
+
+  // Called when a goaway frame opaque data is available.
+  // |goaway_data| A buffer containing the opaque GOAWAY data chunk received.
+  // |len| The length of the header data buffer. A length of zero indicates
+  //       that the header data block has been completely sent.
+  // When this function returns true the visitor indicates that it accepted
+  // all of the data. Returning false indicates that that an error has
+  // occurred while processing the data. Default implementation returns true.
+  virtual bool OnGoAwayFrameData(const char* goaway_data, size_t len);
+
+  // Called when a PUSH_PROMISE frame is received.
+  // Note that header block data is not included. See OnHeaderFrameStart().
+  virtual void OnPushPromise(SpdyStreamId stream_id,
+                             SpdyStreamId promised_stream_id,
+                             bool end) = 0;
+
+  // Called when a CONTINUATION frame is received.
+  // Note that header block data is not included. See OnHeaderFrameStart().
+  virtual void OnContinuation(SpdyStreamId stream_id, bool end) = 0;
+
+  // Called when an ALTSVC frame has been parsed.
+  virtual void OnAltSvc(
+      SpdyStreamId /*stream_id*/,
+      SpdyStringPiece /*origin*/,
+      const SpdyAltSvcWireFormat::AlternativeServiceVector& /*altsvc_vector*/) {
+  }
+
+  // Called when a PRIORITY frame is received.
+  // |stream_id| The stream to update the priority of.
+  // |parent_stream_id| The parent stream of |stream_id|.
+  // |weight| Stream weight, in the range [1, 256].
+  // |exclusive| Whether |stream_id| should be an only child of
+  //     |parent_stream_id|.
+  virtual void OnPriority(SpdyStreamId stream_id,
+                          SpdyStreamId parent_stream_id,
+                          int weight,
+                          bool exclusive) = 0;
+
+  // Called when a frame type we don't recognize is received.
+  // Return true if this appears to be a valid extension frame, false otherwise.
+  // We distinguish between extension frames and nonsense by checking
+  // whether the stream id is valid.
+  virtual bool OnUnknownFrame(SpdyStreamId stream_id, uint8_t frame_type) = 0;
+};
+
+class SPDY_EXPORT_PRIVATE ExtensionVisitorInterface {
+ public:
+  virtual ~ExtensionVisitorInterface() {}
+
+  // Called when SETTINGS are received, including non-standard SETTINGS.
+  virtual void OnSetting(SpdySettingsId id, uint32_t value) = 0;
+
+  // Called when non-standard frames are received.
+  virtual bool OnFrameHeader(SpdyStreamId stream_id,
+                             size_t length,
+                             uint8_t type,
+                             uint8_t flags) = 0;
+
+  // The payload for a single frame may be delivered as multiple calls to
+  // OnFramePayload. Since the length field is passed in OnFrameHeader, there is
+  // no explicit indication of the end of the frame payload.
+  virtual void OnFramePayload(const char* data, size_t len) = 0;
+};
+
+}  // namespace spdy
+
+#endif  // QUICHE_SPDY_CORE_HTTP2_FRAME_DECODER_ADAPTER_H_
diff --git a/spdy/core/mock_spdy_framer_visitor.cc b/spdy/core/mock_spdy_framer_visitor.cc
new file mode 100644
index 0000000..053c255
--- /dev/null
+++ b/spdy/core/mock_spdy_framer_visitor.cc
@@ -0,0 +1,19 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "net/third_party/quiche/src/spdy/core/mock_spdy_framer_visitor.h"
+
+namespace spdy {
+
+namespace test {
+
+MockSpdyFramerVisitor::MockSpdyFramerVisitor() {
+  DelegateHeaderHandling();
+}
+
+MockSpdyFramerVisitor::~MockSpdyFramerVisitor() = default;
+
+}  // namespace test
+
+}  // namespace spdy
diff --git a/spdy/core/mock_spdy_framer_visitor.h b/spdy/core/mock_spdy_framer_visitor.h
new file mode 100644
index 0000000..124efe5
--- /dev/null
+++ b/spdy/core/mock_spdy_framer_visitor.h
@@ -0,0 +1,103 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef QUICHE_SPDY_CORE_MOCK_SPDY_FRAMER_VISITOR_H_
+#define QUICHE_SPDY_CORE_MOCK_SPDY_FRAMER_VISITOR_H_
+
+#include <cstdint>
+#include <memory>
+
+#include "testing/gmock/include/gmock/gmock.h"
+#include "net/third_party/quiche/src/spdy/core/http2_frame_decoder_adapter.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_test_utils.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_ptr_util.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string_piece.h"
+
+namespace spdy {
+
+namespace test {
+
+class MockSpdyFramerVisitor : public SpdyFramerVisitorInterface {
+ public:
+  MockSpdyFramerVisitor();
+  ~MockSpdyFramerVisitor() override;
+
+  MOCK_METHOD1(OnError,
+               void(http2::Http2DecoderAdapter::SpdyFramerError error));
+  MOCK_METHOD3(OnDataFrameHeader,
+               void(SpdyStreamId stream_id, size_t length, bool fin));
+  MOCK_METHOD3(OnStreamFrameData,
+               void(SpdyStreamId stream_id, const char* data, size_t len));
+  MOCK_METHOD1(OnStreamEnd, void(SpdyStreamId stream_id));
+  MOCK_METHOD2(OnStreamPadLength, void(SpdyStreamId stream_id, size_t value));
+  MOCK_METHOD2(OnStreamPadding, void(SpdyStreamId stream_id, size_t len));
+  MOCK_METHOD1(OnHeaderFrameStart,
+               SpdyHeadersHandlerInterface*(SpdyStreamId stream_id));
+  MOCK_METHOD1(OnHeaderFrameEnd, void(SpdyStreamId stream_id));
+  MOCK_METHOD2(OnRstStream,
+               void(SpdyStreamId stream_id, SpdyErrorCode error_code));
+  MOCK_METHOD0(OnSettings, void());
+  MOCK_METHOD2(OnSetting, void(SpdySettingsId id, uint32_t value));
+  MOCK_METHOD2(OnPing, void(SpdyPingId unique_id, bool is_ack));
+  MOCK_METHOD0(OnSettingsEnd, void());
+  MOCK_METHOD2(OnGoAway,
+               void(SpdyStreamId last_accepted_stream_id,
+                    SpdyErrorCode error_code));
+  MOCK_METHOD7(OnHeaders,
+               void(SpdyStreamId stream_id,
+                    bool has_priority,
+                    int weight,
+                    SpdyStreamId parent_stream_id,
+                    bool exclusive,
+                    bool fin,
+                    bool end));
+  MOCK_METHOD2(OnWindowUpdate,
+               void(SpdyStreamId stream_id, int delta_window_size));
+  MOCK_METHOD3(OnPushPromise,
+               void(SpdyStreamId stream_id,
+                    SpdyStreamId promised_stream_id,
+                    bool end));
+  MOCK_METHOD2(OnContinuation, void(SpdyStreamId stream_id, bool end));
+  MOCK_METHOD3(OnAltSvc,
+               void(SpdyStreamId stream_id,
+                    SpdyStringPiece origin,
+                    const SpdyAltSvcWireFormat::AlternativeServiceVector&
+                        altsvc_vector));
+  MOCK_METHOD4(OnPriority,
+               void(SpdyStreamId stream_id,
+                    SpdyStreamId parent_stream_id,
+                    int weight,
+                    bool exclusive));
+  MOCK_METHOD2(OnUnknownFrame,
+               bool(SpdyStreamId stream_id, uint8_t frame_type));
+
+  void DelegateHeaderHandling() {
+    ON_CALL(*this, OnHeaderFrameStart(testing::_))
+        .WillByDefault(testing::Invoke(
+            this, &MockSpdyFramerVisitor::ReturnTestHeadersHandler));
+    ON_CALL(*this, OnHeaderFrameEnd(testing::_))
+        .WillByDefault(testing::Invoke(
+            this, &MockSpdyFramerVisitor::ResetTestHeadersHandler));
+  }
+
+  SpdyHeadersHandlerInterface* ReturnTestHeadersHandler(
+      SpdyStreamId /* stream_id */) {
+    if (headers_handler_ == nullptr) {
+      headers_handler_ = SpdyMakeUnique<TestHeadersHandler>();
+    }
+    return headers_handler_.get();
+  }
+
+  void ResetTestHeadersHandler(SpdyStreamId /* stream_id */) {
+    headers_handler_.reset();
+  }
+
+  std::unique_ptr<SpdyHeadersHandlerInterface> headers_handler_;
+};
+
+}  // namespace test
+
+}  // namespace spdy
+
+#endif  // QUICHE_SPDY_CORE_MOCK_SPDY_FRAMER_VISITOR_H_
diff --git a/spdy/core/priority_write_scheduler.h b/spdy/core/priority_write_scheduler.h
new file mode 100644
index 0000000..d5c3c44
--- /dev/null
+++ b/spdy/core/priority_write_scheduler.h
@@ -0,0 +1,322 @@
+// Copyright (c) 2015 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef QUICHE_SPDY_CORE_PRIORITY_WRITE_SCHEDULER_H_
+#define QUICHE_SPDY_CORE_PRIORITY_WRITE_SCHEDULER_H_
+
+#include <algorithm>
+#include <cstddef>
+#include <cstdint>
+#include <tuple>
+#include <unordered_map>
+#include <utility>
+#include <vector>
+
+#include "base/logging.h"
+#include "net/third_party/quiche/src/http2/platform/api/http2_containers.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_protocol.h"
+#include "net/third_party/quiche/src/spdy/core/write_scheduler.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_bug_tracker.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_macros.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string_utils.h"
+
+namespace spdy {
+
+namespace test {
+template <typename StreamIdType>
+class PriorityWriteSchedulerPeer;
+}
+
+// WriteScheduler implementation that manages the order in which streams are
+// written using the SPDY priority scheme described at:
+// https://www.chromium.org/spdy/spdy-protocol/spdy-protocol-draft3-1#TOC-2.3.3-Stream-priority
+//
+// Internally, PriorityWriteScheduler consists of 8 PriorityInfo objects, one
+// for each priority value.  Each PriorityInfo contains a list of streams of
+// that priority that are ready to write, as well as a timestamp of the last
+// I/O event that occurred for a stream of that priority.
+//
+// DO NOT USE. Deprecated.
+template <typename StreamIdType>
+class PriorityWriteScheduler : public WriteScheduler<StreamIdType> {
+ public:
+  using typename WriteScheduler<StreamIdType>::StreamPrecedenceType;
+
+  // Creates scheduler with no streams.
+  PriorityWriteScheduler() = default;
+
+  void RegisterStream(StreamIdType stream_id,
+                      const StreamPrecedenceType& precedence) override {
+    // TODO(mpw): verify |precedence.is_spdy3_priority() == true| once
+    //   Http2PriorityWriteScheduler enabled for HTTP/2.
+
+    // parent_id not used here, but may as well validate it.  However,
+    // parent_id may legitimately not be registered yet--see b/15676312.
+    StreamIdType parent_id = precedence.parent_id();
+    SPDY_DVLOG_IF(
+        1, parent_id != kHttp2RootStreamId && !StreamRegistered(parent_id))
+        << "Parent stream " << parent_id << " not registered";
+
+    if (stream_id == kHttp2RootStreamId) {
+      SPDY_BUG << "Stream " << kHttp2RootStreamId << " already registered";
+      return;
+    }
+    StreamInfo stream_info = {precedence.spdy3_priority(), stream_id, false};
+    bool inserted =
+        stream_infos_.insert(std::make_pair(stream_id, stream_info)).second;
+    SPDY_BUG_IF(!inserted) << "Stream " << stream_id << " already registered";
+  }
+
+  void UnregisterStream(StreamIdType stream_id) override {
+    auto it = stream_infos_.find(stream_id);
+    if (it == stream_infos_.end()) {
+      SPDY_BUG << "Stream " << stream_id << " not registered";
+      return;
+    }
+    StreamInfo& stream_info = it->second;
+    if (stream_info.ready) {
+      bool erased =
+          Erase(&priority_infos_[stream_info.priority].ready_list, stream_info);
+      DCHECK(erased);
+    }
+    stream_infos_.erase(it);
+  }
+
+  bool StreamRegistered(StreamIdType stream_id) const override {
+    return stream_infos_.find(stream_id) != stream_infos_.end();
+  }
+
+  StreamPrecedenceType GetStreamPrecedence(
+      StreamIdType stream_id) const override {
+    auto it = stream_infos_.find(stream_id);
+    if (it == stream_infos_.end()) {
+      DVLOG(1) << "Stream " << stream_id << " not registered";
+      return StreamPrecedenceType(kV3LowestPriority);
+    }
+    return StreamPrecedenceType(it->second.priority);
+  }
+
+  void UpdateStreamPrecedence(StreamIdType stream_id,
+                              const StreamPrecedenceType& precedence) override {
+    // TODO(mpw): verify |precedence.is_spdy3_priority() == true| once
+    //   Http2PriorityWriteScheduler enabled for HTTP/2.
+
+    // parent_id not used here, but may as well validate it.  However,
+    // parent_id may legitimately not be registered yet--see b/15676312.
+    StreamIdType parent_id = precedence.parent_id();
+    SPDY_DVLOG_IF(
+        1, parent_id != kHttp2RootStreamId && !StreamRegistered(parent_id))
+        << "Parent stream " << parent_id << " not registered";
+
+    auto it = stream_infos_.find(stream_id);
+    if (it == stream_infos_.end()) {
+      // TODO(mpw): add to stream_infos_ on demand--see b/15676312.
+      DVLOG(1) << "Stream " << stream_id << " not registered";
+      return;
+    }
+    StreamInfo& stream_info = it->second;
+    SpdyPriority new_priority = precedence.spdy3_priority();
+    if (stream_info.priority == new_priority) {
+      return;
+    }
+    if (stream_info.ready) {
+      bool erased =
+          Erase(&priority_infos_[stream_info.priority].ready_list, stream_info);
+      DCHECK(erased);
+      priority_infos_[new_priority].ready_list.push_back(&stream_info);
+      ++num_ready_streams_;
+    }
+    stream_info.priority = new_priority;
+  }
+
+  std::vector<StreamIdType> GetStreamChildren(
+      StreamIdType stream_id) const override {
+    return std::vector<StreamIdType>();
+  }
+
+  void RecordStreamEventTime(StreamIdType stream_id,
+                             int64_t now_in_usec) override {
+    auto it = stream_infos_.find(stream_id);
+    if (it == stream_infos_.end()) {
+      SPDY_BUG << "Stream " << stream_id << " not registered";
+      return;
+    }
+    PriorityInfo& priority_info = priority_infos_[it->second.priority];
+    priority_info.last_event_time_usec =
+        std::max(priority_info.last_event_time_usec, now_in_usec);
+  }
+
+  int64_t GetLatestEventWithPrecedence(StreamIdType stream_id) const override {
+    auto it = stream_infos_.find(stream_id);
+    if (it == stream_infos_.end()) {
+      SPDY_BUG << "Stream " << stream_id << " not registered";
+      return 0;
+    }
+    int64_t last_event_time_usec = 0;
+    const StreamInfo& stream_info = it->second;
+    for (SpdyPriority p = kV3HighestPriority; p < stream_info.priority; ++p) {
+      last_event_time_usec = std::max(last_event_time_usec,
+                                      priority_infos_[p].last_event_time_usec);
+    }
+    return last_event_time_usec;
+  }
+
+  StreamIdType PopNextReadyStream() override {
+    return std::get<0>(PopNextReadyStreamAndPrecedence());
+  }
+
+  // Returns the next ready stream and its precedence.
+  std::tuple<StreamIdType, StreamPrecedenceType>
+  PopNextReadyStreamAndPrecedence() override {
+    for (SpdyPriority p = kV3HighestPriority; p <= kV3LowestPriority; ++p) {
+      ReadyList& ready_list = priority_infos_[p].ready_list;
+      if (!ready_list.empty()) {
+        StreamInfo* info = ready_list.front();
+        ready_list.pop_front();
+        --num_ready_streams_;
+
+        DCHECK(stream_infos_.find(info->stream_id) != stream_infos_.end());
+        info->ready = false;
+        return std::make_tuple(info->stream_id,
+                               StreamPrecedenceType(info->priority));
+      }
+    }
+    SPDY_BUG << "No ready streams available";
+    return std::make_tuple(0, StreamPrecedenceType(kV3LowestPriority));
+  }
+
+  bool ShouldYield(StreamIdType stream_id) const override {
+    auto it = stream_infos_.find(stream_id);
+    if (it == stream_infos_.end()) {
+      SPDY_BUG << "Stream " << stream_id << " not registered";
+      return false;
+    }
+
+    // If there's a higher priority stream, this stream should yield.
+    const StreamInfo& stream_info = it->second;
+    for (SpdyPriority p = kV3HighestPriority; p < stream_info.priority; ++p) {
+      if (!priority_infos_[p].ready_list.empty()) {
+        return true;
+      }
+    }
+
+    // If this priority level is empty, or this stream is the next up, there's
+    // no need to yield.
+    const auto& ready_list = priority_infos_[it->second.priority].ready_list;
+    if (ready_list.empty() || ready_list.front()->stream_id == stream_id) {
+      return false;
+    }
+
+    // There are other streams in this priority level which take precedence.
+    // Yield.
+    return true;
+  }
+
+  void MarkStreamReady(StreamIdType stream_id, bool add_to_front) override {
+    auto it = stream_infos_.find(stream_id);
+    if (it == stream_infos_.end()) {
+      SPDY_BUG << "Stream " << stream_id << " not registered";
+      return;
+    }
+    StreamInfo& stream_info = it->second;
+    if (stream_info.ready) {
+      return;
+    }
+    ReadyList& ready_list = priority_infos_[stream_info.priority].ready_list;
+    if (add_to_front) {
+      ready_list.push_front(&stream_info);
+    } else {
+      ready_list.push_back(&stream_info);
+    }
+    ++num_ready_streams_;
+    stream_info.ready = true;
+  }
+
+  void MarkStreamNotReady(StreamIdType stream_id) override {
+    auto it = stream_infos_.find(stream_id);
+    if (it == stream_infos_.end()) {
+      SPDY_BUG << "Stream " << stream_id << " not registered";
+      return;
+    }
+    StreamInfo& stream_info = it->second;
+    if (!stream_info.ready) {
+      return;
+    }
+    bool erased =
+        Erase(&priority_infos_[stream_info.priority].ready_list, stream_info);
+    DCHECK(erased);
+    stream_info.ready = false;
+  }
+
+  // Returns true iff the number of ready streams is non-zero.
+  bool HasReadyStreams() const override { return num_ready_streams_ > 0; }
+
+  // Returns the number of ready streams.
+  size_t NumReadyStreams() const override { return num_ready_streams_; }
+
+  SpdyString DebugString() const override {
+    return SpdyStrCat(
+        "PriorityWriteScheduler {num_streams=", stream_infos_.size(),
+        " num_ready_streams=", NumReadyStreams(), "}");
+  }
+
+  // Returns true if a stream is ready.
+  bool IsStreamReady(StreamIdType stream_id) const {
+    auto it = stream_infos_.find(stream_id);
+    if (it == stream_infos_.end()) {
+      DLOG(INFO) << "Stream " << stream_id << " not registered";
+      return false;
+    }
+    return it->second.ready;
+  }
+
+ private:
+  friend class test::PriorityWriteSchedulerPeer<StreamIdType>;
+
+  // State kept for all registered streams. All ready streams have ready = true
+  // and should be present in priority_infos_[priority].ready_list.
+  struct StreamInfo {
+    SpdyPriority priority;
+    StreamIdType stream_id;
+    bool ready;
+  };
+
+  // O(1) size lookup, O(1) insert at front or back (amortized).
+  using ReadyList = http2::Http2Deque<StreamInfo*>;
+
+  // State kept for each priority level.
+  struct PriorityInfo {
+    // IDs of streams that are ready to write.
+    ReadyList ready_list;
+    // Time of latest write event for stream of this priority, in microseconds.
+    int64_t last_event_time_usec = 0;
+  };
+
+  typedef std::unordered_map<StreamIdType, StreamInfo> StreamInfoMap;
+
+  // Erases first occurrence (which should be the only one) of |info| in
+  // |ready_list|, returning true if found (and erased), or false otherwise.
+  // Decrements |num_ready_streams_| if an entry is erased.
+  bool Erase(ReadyList* ready_list, const StreamInfo& info) {
+    auto it = std::find(ready_list->begin(), ready_list->end(), &info);
+    if (it == ready_list->end()) {
+      return false;
+    }
+    ready_list->erase(it);
+    --num_ready_streams_;
+    return true;
+  }
+
+  // Number of ready streams.
+  size_t num_ready_streams_ = 0;
+  // Per-priority state, including ready lists.
+  PriorityInfo priority_infos_[kV3LowestPriority + 1];
+  // StreamInfos for all registered streams.
+  StreamInfoMap stream_infos_;
+};
+
+}  // namespace spdy
+
+#endif  // QUICHE_SPDY_CORE_PRIORITY_WRITE_SCHEDULER_H_
diff --git a/spdy/core/priority_write_scheduler_test.cc b/spdy/core/priority_write_scheduler_test.cc
new file mode 100644
index 0000000..a285cb2
--- /dev/null
+++ b/spdy/core/priority_write_scheduler_test.cc
@@ -0,0 +1,371 @@
+// Copyright (c) 2015 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "net/third_party/quiche/src/spdy/core/priority_write_scheduler.h"
+
+#include "testing/gtest/include/gtest/gtest.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_protocol.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_test_utils.h"
+
+namespace spdy {
+namespace test {
+
+template <typename StreamIdType>
+class PriorityWriteSchedulerPeer {
+ public:
+  explicit PriorityWriteSchedulerPeer(
+      PriorityWriteScheduler<StreamIdType>* scheduler)
+      : scheduler_(scheduler) {}
+
+  size_t NumReadyStreams(SpdyPriority priority) const {
+    return scheduler_->priority_infos_[priority].ready_list.size();
+  }
+
+ private:
+  PriorityWriteScheduler<StreamIdType>* scheduler_;
+};
+
+namespace {
+
+class PriorityWriteSchedulerTest : public ::testing::Test {
+ public:
+  PriorityWriteSchedulerTest() : peer_(&scheduler_) {}
+
+  PriorityWriteScheduler<SpdyStreamId> scheduler_;
+  PriorityWriteSchedulerPeer<SpdyStreamId> peer_;
+};
+
+TEST_F(PriorityWriteSchedulerTest, RegisterUnregisterStreams) {
+  EXPECT_FALSE(scheduler_.HasReadyStreams());
+  EXPECT_FALSE(scheduler_.StreamRegistered(1));
+  scheduler_.RegisterStream(1, SpdyStreamPrecedence(1));
+  EXPECT_TRUE(scheduler_.StreamRegistered(1));
+
+  // Root stream counts as already registered.
+  EXPECT_SPDY_BUG(
+      scheduler_.RegisterStream(kHttp2RootStreamId, SpdyStreamPrecedence(1)),
+      "Stream 0 already registered");
+
+  // Try redundant registrations.
+  EXPECT_SPDY_BUG(scheduler_.RegisterStream(1, SpdyStreamPrecedence(1)),
+                  "Stream 1 already registered");
+  EXPECT_SPDY_BUG(scheduler_.RegisterStream(1, SpdyStreamPrecedence(2)),
+                  "Stream 1 already registered");
+
+  scheduler_.RegisterStream(2, SpdyStreamPrecedence(3));
+
+  // Verify registration != ready.
+  EXPECT_FALSE(scheduler_.HasReadyStreams());
+
+  scheduler_.UnregisterStream(1);
+  scheduler_.UnregisterStream(2);
+
+  // Try redundant unregistration.
+  EXPECT_SPDY_BUG(scheduler_.UnregisterStream(1), "Stream 1 not registered");
+  EXPECT_SPDY_BUG(scheduler_.UnregisterStream(2), "Stream 2 not registered");
+}
+
+TEST_F(PriorityWriteSchedulerTest, RegisterStreamWithHttp2StreamDependency) {
+  EXPECT_FALSE(scheduler_.HasReadyStreams());
+  EXPECT_FALSE(scheduler_.StreamRegistered(1));
+  scheduler_.RegisterStream(
+      1, SpdyStreamPrecedence(kHttp2RootStreamId, 123, false));
+  EXPECT_TRUE(scheduler_.StreamRegistered(1));
+  EXPECT_TRUE(scheduler_.GetStreamPrecedence(1).is_spdy3_priority());
+  EXPECT_EQ(3, scheduler_.GetStreamPrecedence(1).spdy3_priority());
+  EXPECT_FALSE(scheduler_.HasReadyStreams());
+
+  EXPECT_SPDY_BUG(scheduler_.RegisterStream(
+                      1, SpdyStreamPrecedence(kHttp2RootStreamId, 256, false)),
+                  "Stream 1 already registered");
+  EXPECT_TRUE(scheduler_.GetStreamPrecedence(1).is_spdy3_priority());
+  EXPECT_EQ(3, scheduler_.GetStreamPrecedence(1).spdy3_priority());
+
+  // Registering stream with a non-existent parent stream is permissible, per
+  // b/15676312, but parent stream will always be reset to 0.
+  scheduler_.RegisterStream(2, SpdyStreamPrecedence(3, 123, false));
+  EXPECT_TRUE(scheduler_.StreamRegistered(2));
+  EXPECT_FALSE(scheduler_.StreamRegistered(3));
+  EXPECT_EQ(kHttp2RootStreamId, scheduler_.GetStreamPrecedence(2).parent_id());
+}
+
+TEST_F(PriorityWriteSchedulerTest, GetStreamPrecedence) {
+  // Unknown streams tolerated due to b/15676312. However, return lowest
+  // priority.
+  EXPECT_EQ(kV3LowestPriority,
+            scheduler_.GetStreamPrecedence(1).spdy3_priority());
+
+  scheduler_.RegisterStream(1, SpdyStreamPrecedence(3));
+  EXPECT_TRUE(scheduler_.GetStreamPrecedence(1).is_spdy3_priority());
+  EXPECT_EQ(3, scheduler_.GetStreamPrecedence(1).spdy3_priority());
+
+  // Redundant registration shouldn't change stream priority.
+  EXPECT_SPDY_BUG(scheduler_.RegisterStream(1, SpdyStreamPrecedence(4)),
+                  "Stream 1 already registered");
+  EXPECT_EQ(3, scheduler_.GetStreamPrecedence(1).spdy3_priority());
+
+  scheduler_.UpdateStreamPrecedence(1, SpdyStreamPrecedence(5));
+  EXPECT_EQ(5, scheduler_.GetStreamPrecedence(1).spdy3_priority());
+
+  // Toggling ready state shouldn't change stream priority.
+  scheduler_.MarkStreamReady(1, true);
+  EXPECT_EQ(5, scheduler_.GetStreamPrecedence(1).spdy3_priority());
+
+  // Test changing priority of ready stream.
+  EXPECT_EQ(1u, peer_.NumReadyStreams(5));
+  scheduler_.UpdateStreamPrecedence(1, SpdyStreamPrecedence(6));
+  EXPECT_EQ(6, scheduler_.GetStreamPrecedence(1).spdy3_priority());
+  EXPECT_EQ(0u, peer_.NumReadyStreams(5));
+  EXPECT_EQ(1u, peer_.NumReadyStreams(6));
+
+  EXPECT_EQ(1u, scheduler_.PopNextReadyStream());
+  EXPECT_EQ(6, scheduler_.GetStreamPrecedence(1).spdy3_priority());
+
+  scheduler_.UnregisterStream(1);
+  EXPECT_EQ(kV3LowestPriority,
+            scheduler_.GetStreamPrecedence(1).spdy3_priority());
+}
+
+TEST_F(PriorityWriteSchedulerTest, PopNextReadyStreamAndPrecedence) {
+  scheduler_.RegisterStream(1, SpdyStreamPrecedence(3));
+  scheduler_.MarkStreamReady(1, true);
+  EXPECT_EQ(std::make_tuple(1u, SpdyStreamPrecedence(3)),
+            scheduler_.PopNextReadyStreamAndPrecedence());
+  scheduler_.UnregisterStream(1);
+}
+
+TEST_F(PriorityWriteSchedulerTest, UpdateStreamPrecedence) {
+  // For the moment, updating stream precedence on a non-registered stream
+  // should have no effect. In the future, it will lazily cause the stream to
+  // be registered (b/15676312).
+  EXPECT_EQ(kV3LowestPriority,
+            scheduler_.GetStreamPrecedence(3).spdy3_priority());
+  EXPECT_FALSE(scheduler_.StreamRegistered(3));
+  scheduler_.UpdateStreamPrecedence(3, SpdyStreamPrecedence(1));
+  EXPECT_FALSE(scheduler_.StreamRegistered(3));
+  EXPECT_EQ(kV3LowestPriority,
+            scheduler_.GetStreamPrecedence(3).spdy3_priority());
+
+  scheduler_.RegisterStream(3, SpdyStreamPrecedence(1));
+  EXPECT_EQ(1, scheduler_.GetStreamPrecedence(3).spdy3_priority());
+  scheduler_.UpdateStreamPrecedence(3, SpdyStreamPrecedence(2));
+  EXPECT_EQ(2, scheduler_.GetStreamPrecedence(3).spdy3_priority());
+
+  // Updating priority of stream to current priority value is valid, but has no
+  // effect.
+  scheduler_.UpdateStreamPrecedence(3, SpdyStreamPrecedence(2));
+  EXPECT_EQ(2, scheduler_.GetStreamPrecedence(3).spdy3_priority());
+
+  // Even though stream 4 is marked ready after stream 5, it should be returned
+  // first by PopNextReadyStream() since it has higher priority.
+  scheduler_.RegisterStream(4, SpdyStreamPrecedence(1));
+  scheduler_.MarkStreamReady(3, false);  // priority 2
+  EXPECT_TRUE(scheduler_.IsStreamReady(3));
+  scheduler_.MarkStreamReady(4, false);  // priority 1
+  EXPECT_TRUE(scheduler_.IsStreamReady(4));
+  EXPECT_EQ(4u, scheduler_.PopNextReadyStream());
+  EXPECT_FALSE(scheduler_.IsStreamReady(4));
+  EXPECT_EQ(3u, scheduler_.PopNextReadyStream());
+  EXPECT_FALSE(scheduler_.IsStreamReady(3));
+
+  // Verify that lowering priority of stream 4 causes it to be returned later
+  // by PopNextReadyStream().
+  scheduler_.MarkStreamReady(3, false);  // priority 2
+  scheduler_.MarkStreamReady(4, false);  // priority 1
+  scheduler_.UpdateStreamPrecedence(4, SpdyStreamPrecedence(3));
+  EXPECT_EQ(3u, scheduler_.PopNextReadyStream());
+  EXPECT_EQ(4u, scheduler_.PopNextReadyStream());
+
+  scheduler_.UnregisterStream(3);
+}
+
+TEST_F(PriorityWriteSchedulerTest,
+       UpdateStreamPrecedenceWithHttp2StreamDependency) {
+  // Unknown streams tolerated due to b/15676312, but should have no effect.
+  scheduler_.UpdateStreamPrecedence(3, SpdyStreamPrecedence(0, 100, false));
+  EXPECT_FALSE(scheduler_.StreamRegistered(3));
+
+  scheduler_.RegisterStream(3, SpdyStreamPrecedence(3));
+  scheduler_.UpdateStreamPrecedence(3, SpdyStreamPrecedence(0, 100, false));
+  EXPECT_TRUE(scheduler_.GetStreamPrecedence(3).is_spdy3_priority());
+  EXPECT_EQ(4, scheduler_.GetStreamPrecedence(3).spdy3_priority());
+
+  scheduler_.UnregisterStream(3);
+  scheduler_.UpdateStreamPrecedence(3, SpdyStreamPrecedence(0, 100, false));
+  EXPECT_FALSE(scheduler_.StreamRegistered(3));
+}
+
+TEST_F(PriorityWriteSchedulerTest, MarkStreamReadyBack) {
+  EXPECT_FALSE(scheduler_.HasReadyStreams());
+  EXPECT_SPDY_BUG(scheduler_.MarkStreamReady(1, false),
+                  "Stream 1 not registered");
+  EXPECT_FALSE(scheduler_.HasReadyStreams());
+  EXPECT_SPDY_BUG(EXPECT_EQ(0u, scheduler_.PopNextReadyStream()),
+                  "No ready streams available");
+
+  // Add a bunch of ready streams to tail of per-priority lists.
+  // Expected order: (P2) 4, (P3) 1, 2, 3, (P5) 5.
+  scheduler_.RegisterStream(1, SpdyStreamPrecedence(3));
+  scheduler_.MarkStreamReady(1, false);
+  EXPECT_TRUE(scheduler_.HasReadyStreams());
+  scheduler_.RegisterStream(2, SpdyStreamPrecedence(3));
+  scheduler_.MarkStreamReady(2, false);
+  scheduler_.RegisterStream(3, SpdyStreamPrecedence(3));
+  scheduler_.MarkStreamReady(3, false);
+  scheduler_.RegisterStream(4, SpdyStreamPrecedence(2));
+  scheduler_.MarkStreamReady(4, false);
+  scheduler_.RegisterStream(5, SpdyStreamPrecedence(5));
+  scheduler_.MarkStreamReady(5, false);
+
+  EXPECT_EQ(4u, scheduler_.PopNextReadyStream());
+  EXPECT_EQ(1u, scheduler_.PopNextReadyStream());
+  EXPECT_EQ(2u, scheduler_.PopNextReadyStream());
+  EXPECT_EQ(3u, scheduler_.PopNextReadyStream());
+  EXPECT_EQ(5u, scheduler_.PopNextReadyStream());
+  EXPECT_SPDY_BUG(EXPECT_EQ(0u, scheduler_.PopNextReadyStream()),
+                  "No ready streams available");
+}
+
+TEST_F(PriorityWriteSchedulerTest, MarkStreamReadyFront) {
+  EXPECT_FALSE(scheduler_.HasReadyStreams());
+  EXPECT_SPDY_BUG(scheduler_.MarkStreamReady(1, true),
+                  "Stream 1 not registered");
+  EXPECT_FALSE(scheduler_.HasReadyStreams());
+  EXPECT_SPDY_BUG(EXPECT_EQ(0u, scheduler_.PopNextReadyStream()),
+                  "No ready streams available");
+
+  // Add a bunch of ready streams to head of per-priority lists.
+  // Expected order: (P2) 4, (P3) 3, 2, 1, (P5) 5
+  scheduler_.RegisterStream(1, SpdyStreamPrecedence(3));
+  scheduler_.MarkStreamReady(1, true);
+  EXPECT_TRUE(scheduler_.HasReadyStreams());
+  scheduler_.RegisterStream(2, SpdyStreamPrecedence(3));
+  scheduler_.MarkStreamReady(2, true);
+  scheduler_.RegisterStream(3, SpdyStreamPrecedence(3));
+  scheduler_.MarkStreamReady(3, true);
+  scheduler_.RegisterStream(4, SpdyStreamPrecedence(2));
+  scheduler_.MarkStreamReady(4, true);
+  scheduler_.RegisterStream(5, SpdyStreamPrecedence(5));
+  scheduler_.MarkStreamReady(5, true);
+
+  EXPECT_EQ(4u, scheduler_.PopNextReadyStream());
+  EXPECT_EQ(3u, scheduler_.PopNextReadyStream());
+  EXPECT_EQ(2u, scheduler_.PopNextReadyStream());
+  EXPECT_EQ(1u, scheduler_.PopNextReadyStream());
+  EXPECT_EQ(5u, scheduler_.PopNextReadyStream());
+  EXPECT_SPDY_BUG(EXPECT_EQ(0u, scheduler_.PopNextReadyStream()),
+                  "No ready streams available");
+}
+
+TEST_F(PriorityWriteSchedulerTest, MarkStreamReadyBackAndFront) {
+  scheduler_.RegisterStream(1, SpdyStreamPrecedence(4));
+  scheduler_.RegisterStream(2, SpdyStreamPrecedence(3));
+  scheduler_.RegisterStream(3, SpdyStreamPrecedence(3));
+  scheduler_.RegisterStream(4, SpdyStreamPrecedence(3));
+  scheduler_.RegisterStream(5, SpdyStreamPrecedence(4));
+  scheduler_.RegisterStream(6, SpdyStreamPrecedence(1));
+
+  // Add a bunch of ready streams to per-priority lists, with variety of adding
+  // at head and tail.
+  // Expected order: (P1) 6, (P3) 4, 2, 3, (P4) 1, 5
+  scheduler_.MarkStreamReady(1, true);
+  scheduler_.MarkStreamReady(2, true);
+  scheduler_.MarkStreamReady(3, false);
+  scheduler_.MarkStreamReady(4, true);
+  scheduler_.MarkStreamReady(5, false);
+  scheduler_.MarkStreamReady(6, true);
+
+  EXPECT_EQ(6u, scheduler_.PopNextReadyStream());
+  EXPECT_EQ(4u, scheduler_.PopNextReadyStream());
+  EXPECT_EQ(2u, scheduler_.PopNextReadyStream());
+  EXPECT_EQ(3u, scheduler_.PopNextReadyStream());
+  EXPECT_EQ(1u, scheduler_.PopNextReadyStream());
+  EXPECT_EQ(5u, scheduler_.PopNextReadyStream());
+  EXPECT_SPDY_BUG(EXPECT_EQ(0u, scheduler_.PopNextReadyStream()),
+                  "No ready streams available");
+}
+
+TEST_F(PriorityWriteSchedulerTest, MarkStreamNotReady) {
+  // Verify ready state reflected in NumReadyStreams().
+  scheduler_.RegisterStream(1, SpdyStreamPrecedence(1));
+  EXPECT_EQ(0u, scheduler_.NumReadyStreams());
+  scheduler_.MarkStreamReady(1, false);
+  EXPECT_EQ(1u, scheduler_.NumReadyStreams());
+  scheduler_.MarkStreamNotReady(1);
+  EXPECT_EQ(0u, scheduler_.NumReadyStreams());
+
+  // Empty pop should fail.
+  EXPECT_SPDY_BUG(EXPECT_EQ(0u, scheduler_.PopNextReadyStream()),
+                  "No ready streams available");
+
+  // Tolerate redundant marking of a stream as not ready.
+  scheduler_.MarkStreamNotReady(1);
+  EXPECT_EQ(0u, scheduler_.NumReadyStreams());
+
+  // Should only be able to mark registered streams.
+  EXPECT_SPDY_BUG(scheduler_.MarkStreamNotReady(3), "Stream 3 not registered");
+}
+
+TEST_F(PriorityWriteSchedulerTest, UnregisterRemovesStream) {
+  scheduler_.RegisterStream(3, SpdyStreamPrecedence(4));
+  scheduler_.MarkStreamReady(3, false);
+  EXPECT_EQ(1u, scheduler_.NumReadyStreams());
+
+  // Unregistering a stream should remove it from set of ready streams.
+  scheduler_.UnregisterStream(3);
+  EXPECT_EQ(0u, scheduler_.NumReadyStreams());
+  EXPECT_SPDY_BUG(EXPECT_EQ(0u, scheduler_.PopNextReadyStream()),
+                  "No ready streams available");
+}
+
+TEST_F(PriorityWriteSchedulerTest, ShouldYield) {
+  scheduler_.RegisterStream(1, SpdyStreamPrecedence(1));
+  scheduler_.RegisterStream(4, SpdyStreamPrecedence(4));
+  scheduler_.RegisterStream(5, SpdyStreamPrecedence(4));
+  scheduler_.RegisterStream(7, SpdyStreamPrecedence(7));
+
+  // Make sure we don't yield when the list is empty.
+  EXPECT_FALSE(scheduler_.ShouldYield(1));
+
+  // Add a low priority stream.
+  scheduler_.MarkStreamReady(4, false);
+  // 4 should not yield to itself.
+  EXPECT_FALSE(scheduler_.ShouldYield(4));
+  // 7 should yield as 4 is blocked and a higher priority.
+  EXPECT_TRUE(scheduler_.ShouldYield(7));
+  // 5 should yield to 4 as they are the same priority.
+  EXPECT_TRUE(scheduler_.ShouldYield(5));
+  // 1 should not yield as 1 is higher priority.
+  EXPECT_FALSE(scheduler_.ShouldYield(1));
+
+  // Add a second stream in that priority class.
+  scheduler_.MarkStreamReady(5, false);
+  // 4 and 5 are both blocked, but 4 is at the front so should not yield.
+  EXPECT_FALSE(scheduler_.ShouldYield(4));
+  EXPECT_TRUE(scheduler_.ShouldYield(5));
+}
+
+TEST_F(PriorityWriteSchedulerTest, GetLatestEventWithPrecedence) {
+  EXPECT_SPDY_BUG(scheduler_.RecordStreamEventTime(3, 5),
+                  "Stream 3 not registered");
+  EXPECT_SPDY_BUG(EXPECT_EQ(0, scheduler_.GetLatestEventWithPrecedence(4)),
+                  "Stream 4 not registered");
+
+  for (int i = 1; i < 5; ++i) {
+    scheduler_.RegisterStream(i, SpdyStreamPrecedence(i));
+  }
+  for (int i = 1; i < 5; ++i) {
+    EXPECT_EQ(0, scheduler_.GetLatestEventWithPrecedence(i));
+  }
+  for (int i = 1; i < 5; ++i) {
+    scheduler_.RecordStreamEventTime(i, i * 100);
+  }
+  for (int i = 1; i < 5; ++i) {
+    EXPECT_EQ((i - 1) * 100, scheduler_.GetLatestEventWithPrecedence(i));
+  }
+}
+
+}  // namespace
+}  // namespace test
+}  // namespace spdy
diff --git a/spdy/core/spdy_alt_svc_wire_format.cc b/spdy/core/spdy_alt_svc_wire_format.cc
new file mode 100644
index 0000000..15234a6
--- /dev/null
+++ b/spdy/core/spdy_alt_svc_wire_format.cc
@@ -0,0 +1,390 @@
+// Copyright (c) 2015 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "net/third_party/quiche/src/spdy/core/spdy_alt_svc_wire_format.h"
+
+#include <algorithm>
+#include <cctype>
+#include <limits>
+
+#include "base/logging.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string_utils.h"
+
+namespace spdy {
+
+namespace {
+
+template <class T>
+bool ParsePositiveIntegerImpl(SpdyStringPiece::const_iterator c,
+                              SpdyStringPiece::const_iterator end,
+                              T* value) {
+  *value = 0;
+  for (; c != end && std::isdigit(*c); ++c) {
+    if (*value > std::numeric_limits<T>::max() / 10) {
+      return false;
+    }
+    *value *= 10;
+    if (*value > std::numeric_limits<T>::max() - (*c - '0')) {
+      return false;
+    }
+    *value += *c - '0';
+  }
+  return (c == end && *value > 0);
+}
+
+}  // namespace
+
+SpdyAltSvcWireFormat::AlternativeService::AlternativeService() = default;
+
+SpdyAltSvcWireFormat::AlternativeService::AlternativeService(
+    const SpdyString& protocol_id,
+    const SpdyString& host,
+    uint16_t port,
+    uint32_t max_age,
+    VersionVector version)
+    : protocol_id(protocol_id),
+      host(host),
+      port(port),
+      max_age(max_age),
+      version(std::move(version)) {}
+
+SpdyAltSvcWireFormat::AlternativeService::~AlternativeService() = default;
+
+SpdyAltSvcWireFormat::AlternativeService::AlternativeService(
+    const AlternativeService& other) = default;
+
+// static
+bool SpdyAltSvcWireFormat::ParseHeaderFieldValue(
+    SpdyStringPiece value,
+    AlternativeServiceVector* altsvc_vector) {
+  // Empty value is invalid according to the specification.
+  if (value.empty()) {
+    return false;
+  }
+  altsvc_vector->clear();
+  if (value == SpdyStringPiece("clear")) {
+    return true;
+  }
+  SpdyStringPiece::const_iterator c = value.begin();
+  while (c != value.end()) {
+    // Parse protocol-id.
+    SpdyStringPiece::const_iterator percent_encoded_protocol_id_end =
+        std::find(c, value.end(), '=');
+    SpdyString protocol_id;
+    if (percent_encoded_protocol_id_end == c ||
+        !PercentDecode(c, percent_encoded_protocol_id_end, &protocol_id)) {
+      return false;
+    }
+    // Check for IETF format for advertising QUIC:
+    // hq=":443";quic=51303338;quic=51303334
+    const bool is_ietf_format_quic = (protocol_id == "hq");
+    c = percent_encoded_protocol_id_end;
+    if (c == value.end()) {
+      return false;
+    }
+    // Parse alt-authority.
+    DCHECK_EQ('=', *c);
+    ++c;
+    if (c == value.end() || *c != '"') {
+      return false;
+    }
+    ++c;
+    SpdyStringPiece::const_iterator alt_authority_begin = c;
+    for (; c != value.end() && *c != '"'; ++c) {
+      // Decode backslash encoding.
+      if (*c != '\\') {
+        continue;
+      }
+      ++c;
+      if (c == value.end()) {
+        return false;
+      }
+    }
+    if (c == alt_authority_begin || c == value.end()) {
+      return false;
+    }
+    DCHECK_EQ('"', *c);
+    SpdyString host;
+    uint16_t port;
+    if (!ParseAltAuthority(alt_authority_begin, c, &host, &port)) {
+      return false;
+    }
+    ++c;
+    // Parse parameters.
+    uint32_t max_age = 86400;
+    VersionVector version;
+    SpdyStringPiece::const_iterator parameters_end =
+        std::find(c, value.end(), ',');
+    while (c != parameters_end) {
+      SkipWhiteSpace(&c, parameters_end);
+      if (c == parameters_end) {
+        break;
+      }
+      if (*c != ';') {
+        return false;
+      }
+      ++c;
+      SkipWhiteSpace(&c, parameters_end);
+      if (c == parameters_end) {
+        break;
+      }
+      SpdyString parameter_name;
+      for (; c != parameters_end && *c != '=' && *c != ' ' && *c != '\t'; ++c) {
+        parameter_name.push_back(tolower(*c));
+      }
+      SkipWhiteSpace(&c, parameters_end);
+      if (c == parameters_end || *c != '=') {
+        return false;
+      }
+      ++c;
+      SkipWhiteSpace(&c, parameters_end);
+      SpdyStringPiece::const_iterator parameter_value_begin = c;
+      for (; c != parameters_end && *c != ';' && *c != ' ' && *c != '\t'; ++c) {
+      }
+      if (c == parameter_value_begin) {
+        return false;
+      }
+      if (parameter_name == "ma") {
+        if (!ParsePositiveInteger32(parameter_value_begin, c, &max_age)) {
+          return false;
+        }
+      } else if (!is_ietf_format_quic && parameter_name == "v") {
+        // Version is a comma separated list of positive integers enclosed in
+        // quotation marks.  Since it can contain commas, which are not
+        // delineating alternative service entries, |parameters_end| and |c| can
+        // be invalid.
+        if (*parameter_value_begin != '"') {
+          return false;
+        }
+        c = std::find(parameter_value_begin + 1, value.end(), '"');
+        if (c == value.end()) {
+          return false;
+        }
+        ++c;
+        parameters_end = std::find(c, value.end(), ',');
+        SpdyStringPiece::const_iterator v_begin = parameter_value_begin + 1;
+        while (v_begin < c) {
+          SpdyStringPiece::const_iterator v_end = v_begin;
+          while (v_end < c - 1 && *v_end != ',') {
+            ++v_end;
+          }
+          uint16_t v;
+          if (!ParsePositiveInteger16(v_begin, v_end, &v)) {
+            return false;
+          }
+          version.push_back(v);
+          v_begin = v_end + 1;
+          if (v_begin == c - 1) {
+            // List ends in comma.
+            return false;
+          }
+        }
+      } else if (is_ietf_format_quic && parameter_name == "quic") {
+        // IETF format for advertising QUIC. Version is hex encoding of QUIC
+        // version tag. Hex-encoded string should not include leading "0x" or
+        // leading zeros.
+        // Example for advertising QUIC versions "Q038" and "Q034":
+        // hq=":443";quic=51303338;quic=51303334
+        if (*parameter_value_begin == '0') {
+          return false;
+        }
+        // Versions will be stored as the uint32_t hex decoding of the param
+        // value string. Example: QUIC version "Q038", which is advertised as:
+        // hq=":443";quic=51303338
+        // ... will be stored in |versions| as 0x51303338.
+        uint32_t quic_version;
+        if (!SpdyHexDecodeToUInt32(SpdyStringPiece(parameter_value_begin,
+                                                   c - parameter_value_begin),
+                                   &quic_version) ||
+            quic_version == 0) {
+          return false;
+        }
+        version.push_back(quic_version);
+      }
+    }
+    altsvc_vector->emplace_back(protocol_id, host, port, max_age, version);
+    for (; c != value.end() && (*c == ' ' || *c == '\t' || *c == ','); ++c) {
+    }
+  }
+  return true;
+}
+
+// static
+SpdyString SpdyAltSvcWireFormat::SerializeHeaderFieldValue(
+    const AlternativeServiceVector& altsvc_vector) {
+  if (altsvc_vector.empty()) {
+    return SpdyString("clear");
+  }
+  const char kNibbleToHex[] = "0123456789ABCDEF";
+  SpdyString value;
+  for (const AlternativeService& altsvc : altsvc_vector) {
+    if (!value.empty()) {
+      value.push_back(',');
+    }
+    // Check for IETF format for advertising QUIC.
+    const bool is_ietf_format_quic = (altsvc.protocol_id == "hq");
+    // Percent escape protocol id according to
+    // http://tools.ietf.org/html/rfc7230#section-3.2.6.
+    for (char c : altsvc.protocol_id) {
+      if (isalnum(c)) {
+        value.push_back(c);
+        continue;
+      }
+      switch (c) {
+        case '!':
+        case '#':
+        case '$':
+        case '&':
+        case '\'':
+        case '*':
+        case '+':
+        case '-':
+        case '.':
+        case '^':
+        case '_':
+        case '`':
+        case '|':
+        case '~':
+          value.push_back(c);
+          break;
+        default:
+          value.push_back('%');
+          // Network byte order is big-endian.
+          value.push_back(kNibbleToHex[c >> 4]);
+          value.push_back(kNibbleToHex[c & 0x0f]);
+          break;
+      }
+    }
+    value.push_back('=');
+    value.push_back('"');
+    for (char c : altsvc.host) {
+      if (c == '"' || c == '\\') {
+        value.push_back('\\');
+      }
+      value.push_back(c);
+    }
+    value.append(SpdyStrCat(":", altsvc.port, "\""));
+    if (altsvc.max_age != 86400) {
+      value.append(SpdyStrCat("; ma=", altsvc.max_age));
+    }
+    if (!altsvc.version.empty()) {
+      if (is_ietf_format_quic) {
+        for (uint32_t quic_version : altsvc.version) {
+          value.append("; quic=");
+          value.append(SpdyHexEncodeUInt32AndTrim(quic_version));
+        }
+      } else {
+        value.append("; v=\"");
+        for (auto it = altsvc.version.begin(); it != altsvc.version.end();
+             ++it) {
+          if (it != altsvc.version.begin()) {
+            value.append(",");
+          }
+          value.append(SpdyStrCat(*it));
+        }
+        value.append("\"");
+      }
+    }
+  }
+  return value;
+}
+
+// static
+void SpdyAltSvcWireFormat::SkipWhiteSpace(SpdyStringPiece::const_iterator* c,
+                                          SpdyStringPiece::const_iterator end) {
+  for (; *c != end && (**c == ' ' || **c == '\t'); ++*c) {
+  }
+}
+
+// static
+bool SpdyAltSvcWireFormat::PercentDecode(SpdyStringPiece::const_iterator c,
+                                         SpdyStringPiece::const_iterator end,
+                                         SpdyString* output) {
+  output->clear();
+  for (; c != end; ++c) {
+    if (*c != '%') {
+      output->push_back(*c);
+      continue;
+    }
+    DCHECK_EQ('%', *c);
+    ++c;
+    if (c == end || !std::isxdigit(*c)) {
+      return false;
+    }
+    // Network byte order is big-endian.
+    char decoded = SpdyHexDigitToInt(*c) << 4;
+    ++c;
+    if (c == end || !std::isxdigit(*c)) {
+      return false;
+    }
+    decoded += SpdyHexDigitToInt(*c);
+    output->push_back(decoded);
+  }
+  return true;
+}
+
+// static
+bool SpdyAltSvcWireFormat::ParseAltAuthority(
+    SpdyStringPiece::const_iterator c,
+    SpdyStringPiece::const_iterator end,
+    SpdyString* host,
+    uint16_t* port) {
+  host->clear();
+  if (c == end) {
+    return false;
+  }
+  if (*c == '[') {
+    for (; c != end && *c != ']'; ++c) {
+      if (*c == '"') {
+        // Port is mandatory.
+        return false;
+      }
+      host->push_back(*c);
+    }
+    if (c == end) {
+      return false;
+    }
+    DCHECK_EQ(']', *c);
+    host->push_back(*c);
+    ++c;
+  } else {
+    for (; c != end && *c != ':'; ++c) {
+      if (*c == '"') {
+        // Port is mandatory.
+        return false;
+      }
+      if (*c == '\\') {
+        ++c;
+        if (c == end) {
+          return false;
+        }
+      }
+      host->push_back(*c);
+    }
+  }
+  if (c == end || *c != ':') {
+    return false;
+  }
+  DCHECK_EQ(':', *c);
+  ++c;
+  return ParsePositiveInteger16(c, end, port);
+}
+
+// static
+bool SpdyAltSvcWireFormat::ParsePositiveInteger16(
+    SpdyStringPiece::const_iterator c,
+    SpdyStringPiece::const_iterator end,
+    uint16_t* value) {
+  return ParsePositiveIntegerImpl<uint16_t>(c, end, value);
+}
+
+// static
+bool SpdyAltSvcWireFormat::ParsePositiveInteger32(
+    SpdyStringPiece::const_iterator c,
+    SpdyStringPiece::const_iterator end,
+    uint32_t* value) {
+  return ParsePositiveIntegerImpl<uint32_t>(c, end, value);
+}
+
+}  // namespace spdy
diff --git a/spdy/core/spdy_alt_svc_wire_format.h b/spdy/core/spdy_alt_svc_wire_format.h
new file mode 100644
index 0000000..ac834bc
--- /dev/null
+++ b/spdy/core/spdy_alt_svc_wire_format.h
@@ -0,0 +1,88 @@
+// Copyright (c) 2015 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+// This file contains data structures and utility functions used for serializing
+// and parsing alternative service header values, common to HTTP/1.1 header
+// fields and HTTP/2 and QUIC ALTSVC frames.  See specification at
+// https://httpwg.github.io/http-extensions/alt-svc.html.
+
+#ifndef QUICHE_SPDY_CORE_SPDY_ALT_SVC_WIRE_FORMAT_H_
+#define QUICHE_SPDY_CORE_SPDY_ALT_SVC_WIRE_FORMAT_H_
+
+#include <cstdint>
+#include <vector>
+
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_containers.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_export.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string_piece.h"
+
+namespace spdy {
+
+namespace test {
+class SpdyAltSvcWireFormatPeer;
+}  // namespace test
+
+class SPDY_EXPORT_PRIVATE SpdyAltSvcWireFormat {
+ public:
+  using VersionVector = SpdyInlinedVector<uint32_t, 8>;
+
+  struct SPDY_EXPORT_PRIVATE AlternativeService {
+    SpdyString protocol_id;
+    SpdyString host;
+
+    // Default is 0: invalid port.
+    uint16_t port = 0;
+    // Default is one day.
+    uint32_t max_age = 86400;
+    // Default is empty: unspecified version.
+    VersionVector version;
+
+    AlternativeService();
+    AlternativeService(const SpdyString& protocol_id,
+                       const SpdyString& host,
+                       uint16_t port,
+                       uint32_t max_age,
+                       VersionVector version);
+    AlternativeService(const AlternativeService& other);
+    ~AlternativeService();
+
+    bool operator==(const AlternativeService& other) const {
+      return protocol_id == other.protocol_id && host == other.host &&
+             port == other.port && version == other.version &&
+             max_age == other.max_age;
+    }
+  };
+  // An empty vector means alternative services should be cleared for given
+  // origin.  Note that the wire format for this is the string "clear", not an
+  // empty value (which is invalid).
+  typedef std::vector<AlternativeService> AlternativeServiceVector;
+
+  friend class test::SpdyAltSvcWireFormatPeer;
+  static bool ParseHeaderFieldValue(SpdyStringPiece value,
+                                    AlternativeServiceVector* altsvc_vector);
+  static SpdyString SerializeHeaderFieldValue(
+      const AlternativeServiceVector& altsvc_vector);
+
+ private:
+  static void SkipWhiteSpace(SpdyStringPiece::const_iterator* c,
+                             SpdyStringPiece::const_iterator end);
+  static bool PercentDecode(SpdyStringPiece::const_iterator c,
+                            SpdyStringPiece::const_iterator end,
+                            SpdyString* output);
+  static bool ParseAltAuthority(SpdyStringPiece::const_iterator c,
+                                SpdyStringPiece::const_iterator end,
+                                SpdyString* host,
+                                uint16_t* port);
+  static bool ParsePositiveInteger16(SpdyStringPiece::const_iterator c,
+                                     SpdyStringPiece::const_iterator end,
+                                     uint16_t* value);
+  static bool ParsePositiveInteger32(SpdyStringPiece::const_iterator c,
+                                     SpdyStringPiece::const_iterator end,
+                                     uint32_t* value);
+};
+
+}  // namespace spdy
+
+#endif  // QUICHE_SPDY_CORE_SPDY_ALT_SVC_WIRE_FORMAT_H_
diff --git a/spdy/core/spdy_alt_svc_wire_format_test.cc b/spdy/core/spdy_alt_svc_wire_format_test.cc
new file mode 100644
index 0000000..c2595f0
--- /dev/null
+++ b/spdy/core/spdy_alt_svc_wire_format_test.cc
@@ -0,0 +1,573 @@
+// Copyright (c) 2015 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "net/third_party/quiche/src/spdy/core/spdy_alt_svc_wire_format.h"
+
+#include "base/logging.h"
+#include "testing/gmock/include/gmock/gmock.h"
+#include "testing/gtest/include/gtest/gtest.h"
+
+namespace spdy {
+
+namespace test {
+
+// Expose all private methods of class SpdyAltSvcWireFormat.
+class SpdyAltSvcWireFormatPeer {
+ public:
+  static void SkipWhiteSpace(SpdyStringPiece::const_iterator* c,
+                             SpdyStringPiece::const_iterator end) {
+    SpdyAltSvcWireFormat::SkipWhiteSpace(c, end);
+  }
+  static bool PercentDecode(SpdyStringPiece::const_iterator c,
+                            SpdyStringPiece::const_iterator end,
+                            SpdyString* output) {
+    return SpdyAltSvcWireFormat::PercentDecode(c, end, output);
+  }
+  static bool ParseAltAuthority(SpdyStringPiece::const_iterator c,
+                                SpdyStringPiece::const_iterator end,
+                                SpdyString* host,
+                                uint16_t* port) {
+    return SpdyAltSvcWireFormat::ParseAltAuthority(c, end, host, port);
+  }
+  static bool ParsePositiveInteger16(SpdyStringPiece::const_iterator c,
+                                     SpdyStringPiece::const_iterator end,
+                                     uint16_t* max_age) {
+    return SpdyAltSvcWireFormat::ParsePositiveInteger16(c, end, max_age);
+  }
+  static bool ParsePositiveInteger32(SpdyStringPiece::const_iterator c,
+                                     SpdyStringPiece::const_iterator end,
+                                     uint32_t* max_age) {
+    return SpdyAltSvcWireFormat::ParsePositiveInteger32(c, end, max_age);
+  }
+};
+
+}  // namespace test
+
+namespace {
+
+// Generate header field values, possibly with multiply defined parameters and
+// random case, and corresponding AlternativeService entries.
+void FuzzHeaderFieldValue(
+    int i,
+    SpdyString* header_field_value,
+    SpdyAltSvcWireFormat::AlternativeService* expected_altsvc) {
+  if (!header_field_value->empty()) {
+    header_field_value->push_back(',');
+  }
+  // TODO(b/77515496): use struct of bools instead of int |i| to generate the
+  // header field value.
+  bool is_ietf_format_quic = (i & 1 << 0) != 0;
+  if (i & 1 << 0) {
+    expected_altsvc->protocol_id = "hq";
+    header_field_value->append("hq=\"");
+  } else {
+    expected_altsvc->protocol_id = "a=b%c";
+    header_field_value->append("a%3Db%25c=\"");
+  }
+  if (i & 1 << 1) {
+    expected_altsvc->host = "foo\"bar\\baz";
+    header_field_value->append("foo\\\"bar\\\\baz");
+  } else {
+    expected_altsvc->host = "";
+  }
+  expected_altsvc->port = 42;
+  header_field_value->append(":42\"");
+  if (i & 1 << 2) {
+    header_field_value->append(" ");
+  }
+  if (i & 3 << 3) {
+    expected_altsvc->max_age = 1111;
+    header_field_value->append(";");
+    if (i & 1 << 3) {
+      header_field_value->append(" ");
+    }
+    header_field_value->append("mA=1111");
+    if (i & 2 << 3) {
+      header_field_value->append(" ");
+    }
+  }
+  if (i & 1 << 5) {
+    header_field_value->append("; J=s");
+  }
+  if (i & 1 << 6) {
+    if (is_ietf_format_quic) {
+      if (i & 1 << 7) {
+        expected_altsvc->version.push_back(0x923457e);
+        header_field_value->append("; quic=923457E");
+      } else {
+        expected_altsvc->version.push_back(1);
+        expected_altsvc->version.push_back(0xFFFFFFFF);
+        header_field_value->append("; quic=1; quic=fFfFffFf");
+      }
+    } else {
+      if (i & i << 7) {
+        expected_altsvc->version.push_back(24);
+        header_field_value->append("; v=\"24\"");
+      } else {
+        expected_altsvc->version.push_back(1);
+        expected_altsvc->version.push_back(65535);
+        header_field_value->append("; v=\"1,65535\"");
+      }
+    }
+  }
+  if (i & 1 << 8) {
+    expected_altsvc->max_age = 999999999;
+    header_field_value->append("; Ma=999999999");
+  }
+  if (i & 1 << 9) {
+    header_field_value->append(";");
+  }
+  if (i & 1 << 10) {
+    header_field_value->append(" ");
+  }
+  if (i & 1 << 11) {
+    header_field_value->append(",");
+  }
+  if (i & 1 << 12) {
+    header_field_value->append(" ");
+  }
+}
+
+// Generate AlternativeService entries and corresponding header field values in
+// canonical form, that is, what SerializeHeaderFieldValue() should output.
+void FuzzAlternativeService(int i,
+                            SpdyAltSvcWireFormat::AlternativeService* altsvc,
+                            SpdyString* expected_header_field_value) {
+  if (!expected_header_field_value->empty()) {
+    expected_header_field_value->push_back(',');
+  }
+  altsvc->protocol_id = "a=b%c";
+  altsvc->port = 42;
+  expected_header_field_value->append("a%3Db%25c=\"");
+  if (i & 1 << 0) {
+    altsvc->host = "foo\"bar\\baz";
+    expected_header_field_value->append("foo\\\"bar\\\\baz");
+  }
+  expected_header_field_value->append(":42\"");
+  if (i & 1 << 1) {
+    altsvc->max_age = 1111;
+    expected_header_field_value->append("; ma=1111");
+  }
+  if (i & 1 << 2) {
+    altsvc->version.push_back(24);
+    altsvc->version.push_back(25);
+    expected_header_field_value->append("; v=\"24,25\"");
+  }
+}
+
+// Tests of public API.
+
+TEST(SpdyAltSvcWireFormatTest, DefaultValues) {
+  SpdyAltSvcWireFormat::AlternativeService altsvc;
+  EXPECT_EQ("", altsvc.protocol_id);
+  EXPECT_EQ("", altsvc.host);
+  EXPECT_EQ(0u, altsvc.port);
+  EXPECT_EQ(86400u, altsvc.max_age);
+  EXPECT_TRUE(altsvc.version.empty());
+}
+
+TEST(SpdyAltSvcWireFormatTest, ParseInvalidEmptyHeaderFieldValue) {
+  SpdyAltSvcWireFormat::AlternativeServiceVector altsvc_vector;
+  ASSERT_FALSE(SpdyAltSvcWireFormat::ParseHeaderFieldValue("", &altsvc_vector));
+}
+
+TEST(SpdyAltSvcWireFormatTest, ParseHeaderFieldValueClear) {
+  SpdyAltSvcWireFormat::AlternativeServiceVector altsvc_vector;
+  ASSERT_TRUE(
+      SpdyAltSvcWireFormat::ParseHeaderFieldValue("clear", &altsvc_vector));
+  EXPECT_EQ(0u, altsvc_vector.size());
+}
+
+// Fuzz test of ParseHeaderFieldValue() with optional whitespaces, ignored
+// parameters, duplicate parameters, trailing space, trailing alternate service
+// separator, etc.  Single alternative service at a time.
+TEST(SpdyAltSvcWireFormatTest, ParseHeaderFieldValue) {
+  for (int i = 0; i < 1 << 13; ++i) {
+    SpdyString header_field_value;
+    SpdyAltSvcWireFormat::AlternativeService expected_altsvc;
+    FuzzHeaderFieldValue(i, &header_field_value, &expected_altsvc);
+    SpdyAltSvcWireFormat::AlternativeServiceVector altsvc_vector;
+    ASSERT_TRUE(SpdyAltSvcWireFormat::ParseHeaderFieldValue(header_field_value,
+                                                            &altsvc_vector));
+    ASSERT_EQ(1u, altsvc_vector.size());
+    EXPECT_EQ(expected_altsvc.protocol_id, altsvc_vector[0].protocol_id);
+    EXPECT_EQ(expected_altsvc.host, altsvc_vector[0].host);
+    EXPECT_EQ(expected_altsvc.port, altsvc_vector[0].port);
+    EXPECT_EQ(expected_altsvc.max_age, altsvc_vector[0].max_age);
+    EXPECT_EQ(expected_altsvc.version, altsvc_vector[0].version);
+
+    // Roundtrip test starting with |altsvc_vector|.
+    SpdyString reserialized_header_field_value =
+        SpdyAltSvcWireFormat::SerializeHeaderFieldValue(altsvc_vector);
+    SpdyAltSvcWireFormat::AlternativeServiceVector roundtrip_altsvc_vector;
+    ASSERT_TRUE(SpdyAltSvcWireFormat::ParseHeaderFieldValue(
+        reserialized_header_field_value, &roundtrip_altsvc_vector));
+    ASSERT_EQ(1u, roundtrip_altsvc_vector.size());
+    EXPECT_EQ(expected_altsvc.protocol_id,
+              roundtrip_altsvc_vector[0].protocol_id);
+    EXPECT_EQ(expected_altsvc.host, roundtrip_altsvc_vector[0].host);
+    EXPECT_EQ(expected_altsvc.port, roundtrip_altsvc_vector[0].port);
+    EXPECT_EQ(expected_altsvc.max_age, roundtrip_altsvc_vector[0].max_age);
+    EXPECT_EQ(expected_altsvc.version, roundtrip_altsvc_vector[0].version);
+  }
+}
+
+// Fuzz test of ParseHeaderFieldValue() with optional whitespaces, ignored
+// parameters, duplicate parameters, trailing space, trailing alternate service
+// separator, etc.  Possibly multiple alternative service at a time.
+TEST(SpdyAltSvcWireFormatTest, ParseHeaderFieldValueMultiple) {
+  for (int i = 0; i < 1 << 13;) {
+    SpdyString header_field_value;
+    SpdyAltSvcWireFormat::AlternativeServiceVector expected_altsvc_vector;
+    // This will generate almost two hundred header field values with two,
+    // three, four, five, six, and seven alternative services each, and
+    // thousands with a single one.
+    do {
+      SpdyAltSvcWireFormat::AlternativeService expected_altsvc;
+      FuzzHeaderFieldValue(i, &header_field_value, &expected_altsvc);
+      expected_altsvc_vector.push_back(expected_altsvc);
+      ++i;
+    } while (i % 6 < i % 7);
+    SpdyAltSvcWireFormat::AlternativeServiceVector altsvc_vector;
+    ASSERT_TRUE(SpdyAltSvcWireFormat::ParseHeaderFieldValue(header_field_value,
+                                                            &altsvc_vector));
+    ASSERT_EQ(expected_altsvc_vector.size(), altsvc_vector.size());
+    for (unsigned int j = 0; j < altsvc_vector.size(); ++j) {
+      EXPECT_EQ(expected_altsvc_vector[j].protocol_id,
+                altsvc_vector[j].protocol_id);
+      EXPECT_EQ(expected_altsvc_vector[j].host, altsvc_vector[j].host);
+      EXPECT_EQ(expected_altsvc_vector[j].port, altsvc_vector[j].port);
+      EXPECT_EQ(expected_altsvc_vector[j].max_age, altsvc_vector[j].max_age);
+      EXPECT_EQ(expected_altsvc_vector[j].version, altsvc_vector[j].version);
+    }
+
+    // Roundtrip test starting with |altsvc_vector|.
+    SpdyString reserialized_header_field_value =
+        SpdyAltSvcWireFormat::SerializeHeaderFieldValue(altsvc_vector);
+    SpdyAltSvcWireFormat::AlternativeServiceVector roundtrip_altsvc_vector;
+    ASSERT_TRUE(SpdyAltSvcWireFormat::ParseHeaderFieldValue(
+        reserialized_header_field_value, &roundtrip_altsvc_vector));
+    ASSERT_EQ(expected_altsvc_vector.size(), roundtrip_altsvc_vector.size());
+    for (unsigned int j = 0; j < roundtrip_altsvc_vector.size(); ++j) {
+      EXPECT_EQ(expected_altsvc_vector[j].protocol_id,
+                roundtrip_altsvc_vector[j].protocol_id);
+      EXPECT_EQ(expected_altsvc_vector[j].host,
+                roundtrip_altsvc_vector[j].host);
+      EXPECT_EQ(expected_altsvc_vector[j].port,
+                roundtrip_altsvc_vector[j].port);
+      EXPECT_EQ(expected_altsvc_vector[j].max_age,
+                roundtrip_altsvc_vector[j].max_age);
+      EXPECT_EQ(expected_altsvc_vector[j].version,
+                roundtrip_altsvc_vector[j].version);
+    }
+  }
+}
+
+TEST(SpdyAltSvcWireFormatTest, SerializeEmptyHeaderFieldValue) {
+  SpdyAltSvcWireFormat::AlternativeServiceVector altsvc_vector;
+  EXPECT_EQ("clear",
+            SpdyAltSvcWireFormat::SerializeHeaderFieldValue(altsvc_vector));
+}
+
+// Test ParseHeaderFieldValue() and SerializeHeaderFieldValue() on the same pair
+// of |expected_header_field_value| and |altsvc|, with and without hostname and
+// each
+// parameter.  Single alternative service at a time.
+TEST(SpdyAltSvcWireFormatTest, RoundTrip) {
+  for (int i = 0; i < 1 << 3; ++i) {
+    SpdyAltSvcWireFormat::AlternativeService altsvc;
+    SpdyString expected_header_field_value;
+    FuzzAlternativeService(i, &altsvc, &expected_header_field_value);
+
+    // Test ParseHeaderFieldValue().
+    SpdyAltSvcWireFormat::AlternativeServiceVector parsed_altsvc_vector;
+    ASSERT_TRUE(SpdyAltSvcWireFormat::ParseHeaderFieldValue(
+        expected_header_field_value, &parsed_altsvc_vector));
+    ASSERT_EQ(1u, parsed_altsvc_vector.size());
+    EXPECT_EQ(altsvc.protocol_id, parsed_altsvc_vector[0].protocol_id);
+    EXPECT_EQ(altsvc.host, parsed_altsvc_vector[0].host);
+    EXPECT_EQ(altsvc.port, parsed_altsvc_vector[0].port);
+    EXPECT_EQ(altsvc.max_age, parsed_altsvc_vector[0].max_age);
+    EXPECT_EQ(altsvc.version, parsed_altsvc_vector[0].version);
+
+    // Test SerializeHeaderFieldValue().
+    SpdyAltSvcWireFormat::AlternativeServiceVector altsvc_vector;
+    altsvc_vector.push_back(altsvc);
+    EXPECT_EQ(expected_header_field_value,
+              SpdyAltSvcWireFormat::SerializeHeaderFieldValue(altsvc_vector));
+  }
+}
+
+// Test ParseHeaderFieldValue() and SerializeHeaderFieldValue() on the same pair
+// of |expected_header_field_value| and |altsvc|, with and without hostname and
+// each
+// parameter.  Multiple alternative services at a time.
+TEST(SpdyAltSvcWireFormatTest, RoundTripMultiple) {
+  SpdyAltSvcWireFormat::AlternativeServiceVector altsvc_vector;
+  SpdyString expected_header_field_value;
+  for (int i = 0; i < 1 << 3; ++i) {
+    SpdyAltSvcWireFormat::AlternativeService altsvc;
+    FuzzAlternativeService(i, &altsvc, &expected_header_field_value);
+    altsvc_vector.push_back(altsvc);
+  }
+
+  // Test ParseHeaderFieldValue().
+  SpdyAltSvcWireFormat::AlternativeServiceVector parsed_altsvc_vector;
+  ASSERT_TRUE(SpdyAltSvcWireFormat::ParseHeaderFieldValue(
+      expected_header_field_value, &parsed_altsvc_vector));
+  ASSERT_EQ(altsvc_vector.size(), parsed_altsvc_vector.size());
+  auto expected_it = altsvc_vector.begin();
+  auto parsed_it = parsed_altsvc_vector.begin();
+  for (; expected_it != altsvc_vector.end(); ++expected_it, ++parsed_it) {
+    EXPECT_EQ(expected_it->protocol_id, parsed_it->protocol_id);
+    EXPECT_EQ(expected_it->host, parsed_it->host);
+    EXPECT_EQ(expected_it->port, parsed_it->port);
+    EXPECT_EQ(expected_it->max_age, parsed_it->max_age);
+    EXPECT_EQ(expected_it->version, parsed_it->version);
+  }
+
+  // Test SerializeHeaderFieldValue().
+  EXPECT_EQ(expected_header_field_value,
+            SpdyAltSvcWireFormat::SerializeHeaderFieldValue(altsvc_vector));
+}
+
+// ParseHeaderFieldValue() should return false on malformed field values:
+// invalid percent encoding, unmatched quotation mark, empty port, non-numeric
+// characters in numeric fields.
+TEST(SpdyAltSvcWireFormatTest, ParseHeaderFieldValueInvalid) {
+  SpdyAltSvcWireFormat::AlternativeServiceVector altsvc_vector;
+  const char* invalid_field_value_array[] = {"a%",
+                                             "a%x",
+                                             "a%b",
+                                             "a%9z",
+                                             "a=",
+                                             "a=\"",
+                                             "a=\"b\"",
+                                             "a=\":\"",
+                                             "a=\"c:\"",
+                                             "a=\"c:foo\"",
+                                             "a=\"c:42foo\"",
+                                             "a=\"b:42\"bar",
+                                             "a=\"b:42\" ; m",
+                                             "a=\"b:42\" ; min-age",
+                                             "a=\"b:42\" ; ma",
+                                             "a=\"b:42\" ; ma=",
+                                             "a=\"b:42\" ; v=\"..\"",
+                                             "a=\"b:42\" ; ma=ma",
+                                             "a=\"b:42\" ; ma=123bar",
+                                             "a=\"b:42\" ; v=24",
+                                             "a=\"b:42\" ; v=24,25",
+                                             "a=\"b:42\" ; v=\"-3\"",
+                                             "a=\"b:42\" ; v=\"1.2\"",
+                                             "a=\"b:42\" ; v=\"24,\""};
+  for (const char* invalid_field_value : invalid_field_value_array) {
+    EXPECT_FALSE(SpdyAltSvcWireFormat::ParseHeaderFieldValue(
+        invalid_field_value, &altsvc_vector))
+        << invalid_field_value;
+  }
+}
+
+// ParseHeaderFieldValue() should return false on a field values truncated
+// before closing quotation mark, without trying to access memory beyond the end
+// of the input.
+TEST(SpdyAltSvcWireFormatTest, ParseTruncatedHeaderFieldValue) {
+  SpdyAltSvcWireFormat::AlternativeServiceVector altsvc_vector;
+  const char* field_value_array[] = {"a=\":137\"", "a=\"foo:137\"",
+                                     "a%25=\"foo\\\"bar\\\\baz:137\""};
+  for (const SpdyString& field_value : field_value_array) {
+    for (size_t len = 1; len < field_value.size(); ++len) {
+      EXPECT_FALSE(SpdyAltSvcWireFormat::ParseHeaderFieldValue(
+          field_value.substr(0, len), &altsvc_vector))
+          << len;
+    }
+  }
+}
+
+// Tests of private methods.
+
+// Test SkipWhiteSpace().
+TEST(SpdyAltSvcWireFormatTest, SkipWhiteSpace) {
+  SpdyStringPiece input("a \tb  ");
+  SpdyStringPiece::const_iterator c = input.begin();
+  test::SpdyAltSvcWireFormatPeer::SkipWhiteSpace(&c, input.end());
+  ASSERT_EQ(input.begin(), c);
+  ++c;
+  test::SpdyAltSvcWireFormatPeer::SkipWhiteSpace(&c, input.end());
+  ASSERT_EQ(input.begin() + 3, c);
+  ++c;
+  test::SpdyAltSvcWireFormatPeer::SkipWhiteSpace(&c, input.end());
+  ASSERT_EQ(input.end(), c);
+}
+
+// Test PercentDecode() on valid input.
+TEST(SpdyAltSvcWireFormatTest, PercentDecodeValid) {
+  SpdyStringPiece input("");
+  SpdyString output;
+  ASSERT_TRUE(test::SpdyAltSvcWireFormatPeer::PercentDecode(
+      input.begin(), input.end(), &output));
+  EXPECT_EQ("", output);
+
+  input = SpdyStringPiece("foo");
+  output.clear();
+  ASSERT_TRUE(test::SpdyAltSvcWireFormatPeer::PercentDecode(
+      input.begin(), input.end(), &output));
+  EXPECT_EQ("foo", output);
+
+  input = SpdyStringPiece("%2ca%5Cb");
+  output.clear();
+  ASSERT_TRUE(test::SpdyAltSvcWireFormatPeer::PercentDecode(
+      input.begin(), input.end(), &output));
+  EXPECT_EQ(",a\\b", output);
+}
+
+// Test PercentDecode() on invalid input.
+TEST(SpdyAltSvcWireFormatTest, PercentDecodeInvalid) {
+  const char* invalid_input_array[] = {"a%", "a%x", "a%b", "%J22", "%9z"};
+  for (const char* invalid_input : invalid_input_array) {
+    SpdyStringPiece input(invalid_input);
+    SpdyString output;
+    EXPECT_FALSE(test::SpdyAltSvcWireFormatPeer::PercentDecode(
+        input.begin(), input.end(), &output))
+        << input;
+  }
+}
+
+// Test ParseAltAuthority() on valid input.
+TEST(SpdyAltSvcWireFormatTest, ParseAltAuthorityValid) {
+  SpdyStringPiece input(":42");
+  SpdyString host;
+  uint16_t port;
+  ASSERT_TRUE(test::SpdyAltSvcWireFormatPeer::ParseAltAuthority(
+      input.begin(), input.end(), &host, &port));
+  EXPECT_TRUE(host.empty());
+  EXPECT_EQ(42, port);
+
+  input = SpdyStringPiece("foo:137");
+  ASSERT_TRUE(test::SpdyAltSvcWireFormatPeer::ParseAltAuthority(
+      input.begin(), input.end(), &host, &port));
+  EXPECT_EQ("foo", host);
+  EXPECT_EQ(137, port);
+
+  input = SpdyStringPiece("[2003:8:0:16::509d:9615]:443");
+  ASSERT_TRUE(test::SpdyAltSvcWireFormatPeer::ParseAltAuthority(
+      input.begin(), input.end(), &host, &port));
+  EXPECT_EQ("[2003:8:0:16::509d:9615]", host);
+  EXPECT_EQ(443, port);
+}
+
+// Test ParseAltAuthority() on invalid input: empty string, no port, zero port,
+// non-digit characters following port.
+TEST(SpdyAltSvcWireFormatTest, ParseAltAuthorityInvalid) {
+  const char* invalid_input_array[] = {"",
+                                       ":",
+                                       "foo:",
+                                       ":bar",
+                                       ":0",
+                                       "foo:0",
+                                       ":12bar",
+                                       "foo:23bar",
+                                       " ",
+                                       ":12 ",
+                                       "foo:12 ",
+                                       "[2003:8:0:16::509d:9615]",
+                                       "[2003:8:0:16::509d:9615]:",
+                                       "[2003:8:0:16::509d:9615]foo:443",
+                                       "[2003:8:0:16::509d:9615:443",
+                                       "2003:8:0:16::509d:9615]:443"};
+  for (const char* invalid_input : invalid_input_array) {
+    SpdyStringPiece input(invalid_input);
+    SpdyString host;
+    uint16_t port;
+    EXPECT_FALSE(test::SpdyAltSvcWireFormatPeer::ParseAltAuthority(
+        input.begin(), input.end(), &host, &port))
+        << input;
+  }
+}
+
+// Test ParseInteger() on valid input.
+TEST(SpdyAltSvcWireFormatTest, ParseIntegerValid) {
+  SpdyStringPiece input("3");
+  uint16_t value;
+  ASSERT_TRUE(test::SpdyAltSvcWireFormatPeer::ParsePositiveInteger16(
+      input.begin(), input.end(), &value));
+  EXPECT_EQ(3, value);
+
+  input = SpdyStringPiece("1337");
+  ASSERT_TRUE(test::SpdyAltSvcWireFormatPeer::ParsePositiveInteger16(
+      input.begin(), input.end(), &value));
+  EXPECT_EQ(1337, value);
+}
+
+// Test ParseIntegerValid() on invalid input: empty, zero, non-numeric, trailing
+// non-numeric characters.
+TEST(SpdyAltSvcWireFormatTest, ParseIntegerInvalid) {
+  const char* invalid_input_array[] = {"", " ", "a", "0", "00", "1 ", "12b"};
+  for (const char* invalid_input : invalid_input_array) {
+    SpdyStringPiece input(invalid_input);
+    uint16_t value;
+    EXPECT_FALSE(test::SpdyAltSvcWireFormatPeer::ParsePositiveInteger16(
+        input.begin(), input.end(), &value))
+        << input;
+  }
+}
+
+// Test ParseIntegerValid() around overflow limit.
+TEST(SpdyAltSvcWireFormatTest, ParseIntegerOverflow) {
+  // Largest possible uint16_t value.
+  SpdyStringPiece input("65535");
+  uint16_t value16;
+  ASSERT_TRUE(test::SpdyAltSvcWireFormatPeer::ParsePositiveInteger16(
+      input.begin(), input.end(), &value16));
+  EXPECT_EQ(65535, value16);
+
+  // Overflow uint16_t, ParsePositiveInteger16() should return false.
+  input = SpdyStringPiece("65536");
+  ASSERT_FALSE(test::SpdyAltSvcWireFormatPeer::ParsePositiveInteger16(
+      input.begin(), input.end(), &value16));
+
+  // However, even if overflow is not checked for, 65536 overflows to 0, which
+  // returns false anyway.  Check for a larger number which overflows to 1.
+  input = SpdyStringPiece("65537");
+  ASSERT_FALSE(test::SpdyAltSvcWireFormatPeer::ParsePositiveInteger16(
+      input.begin(), input.end(), &value16));
+
+  // Largest possible uint32_t value.
+  input = SpdyStringPiece("4294967295");
+  uint32_t value32;
+  ASSERT_TRUE(test::SpdyAltSvcWireFormatPeer::ParsePositiveInteger32(
+      input.begin(), input.end(), &value32));
+  EXPECT_EQ(4294967295, value32);
+
+  // Overflow uint32_t, ParsePositiveInteger32() should return false.
+  input = SpdyStringPiece("4294967296");
+  ASSERT_FALSE(test::SpdyAltSvcWireFormatPeer::ParsePositiveInteger32(
+      input.begin(), input.end(), &value32));
+
+  // However, even if overflow is not checked for, 4294967296 overflows to 0,
+  // which returns false anyway.  Check for a larger number which overflows to
+  // 1.
+  input = SpdyStringPiece("4294967297");
+  ASSERT_FALSE(test::SpdyAltSvcWireFormatPeer::ParsePositiveInteger32(
+      input.begin(), input.end(), &value32));
+}
+
+// Test parsing an Alt-Svc entry with IP literal hostname.
+// Regression test for https://crbug.com/664173.
+TEST(SpdyAltSvcWireFormatTest, ParseIPLiteral) {
+  const char* input =
+      "quic=\"[2003:8:0:16::509d:9615]:443\"; v=\"36,35\"; ma=60";
+  SpdyAltSvcWireFormat::AlternativeServiceVector altsvc_vector;
+  ASSERT_TRUE(
+      SpdyAltSvcWireFormat::ParseHeaderFieldValue(input, &altsvc_vector));
+  EXPECT_EQ(1u, altsvc_vector.size());
+  EXPECT_EQ("quic", altsvc_vector[0].protocol_id);
+  EXPECT_EQ("[2003:8:0:16::509d:9615]", altsvc_vector[0].host);
+  EXPECT_EQ(443u, altsvc_vector[0].port);
+  EXPECT_EQ(60u, altsvc_vector[0].max_age);
+  EXPECT_THAT(altsvc_vector[0].version, ::testing::ElementsAre(36, 35));
+}
+
+}  // namespace
+
+}  // namespace spdy
diff --git a/spdy/core/spdy_bitmasks.h b/spdy/core/spdy_bitmasks.h
new file mode 100644
index 0000000..657bd17
--- /dev/null
+++ b/spdy/core/spdy_bitmasks.h
@@ -0,0 +1,18 @@
+// Copyright (c) 2012 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef QUICHE_SPDY_CORE_SPDY_BITMASKS_H_
+#define QUICHE_SPDY_CORE_SPDY_BITMASKS_H_
+
+namespace spdy {
+
+// StreamId mask from the SpdyHeader
+const unsigned int kStreamIdMask = 0x7fffffff;
+
+// Mask the lower 24 bits.
+const unsigned int kLengthMask = 0xffffff;
+
+}  // namespace spdy
+
+#endif  // QUICHE_SPDY_CORE_SPDY_BITMASKS_H_
diff --git a/spdy/core/spdy_deframer_visitor.cc b/spdy/core/spdy_deframer_visitor.cc
new file mode 100644
index 0000000..76188e9
--- /dev/null
+++ b/spdy/core/spdy_deframer_visitor.cc
@@ -0,0 +1,1028 @@
+// Copyright 2016 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "net/third_party/quiche/src/spdy/core/spdy_deframer_visitor.h"
+
+#include <stdlib.h>
+
+#include <algorithm>
+#include <cstdint>
+#include <limits>
+#include <memory>
+
+#include "base/logging.h"
+#include "testing/gmock/include/gmock/gmock.h"
+#include "net/third_party/quiche/src/http2/platform/api/http2_macros.h"
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_constants.h"
+#include "net/third_party/quiche/src/spdy/core/mock_spdy_framer_visitor.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_frame_reader.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_protocol.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_test_utils.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_flags.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_ptr_util.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string_piece.h"
+
+using ::testing::AssertionFailure;
+using ::testing::AssertionResult;
+using ::testing::AssertionSuccess;
+
+namespace spdy {
+namespace test {
+
+// Specify whether to process headers as request or response in visitor-related
+// params.
+enum class HeaderDirection { REQUEST, RESPONSE };
+
+// Types of HTTP/2 frames, per RFC 7540.
+// TODO(jamessynge): Switch to using http2/http2_constants.h when ready.
+enum Http2FrameType {
+  DATA = 0,
+  HEADERS = 1,
+  PRIORITY = 2,
+  RST_STREAM = 3,
+  SETTINGS = 4,
+  PUSH_PROMISE = 5,
+  PING = 6,
+  GOAWAY = 7,
+  WINDOW_UPDATE = 8,
+  CONTINUATION = 9,
+  ALTSVC = 10,
+
+  // Not a frame type.
+  UNSET = -1,
+  UNKNOWN = -2,
+};
+
+// TODO(jamessynge): Switch to using http2/http2_constants.h when ready.
+const char* Http2FrameTypeToString(Http2FrameType v) {
+  switch (v) {
+    case DATA:
+      return "DATA";
+    case HEADERS:
+      return "HEADERS";
+    case PRIORITY:
+      return "PRIORITY";
+    case RST_STREAM:
+      return "RST_STREAM";
+    case SETTINGS:
+      return "SETTINGS";
+    case PUSH_PROMISE:
+      return "PUSH_PROMISE";
+    case PING:
+      return "PING";
+    case GOAWAY:
+      return "GOAWAY";
+    case WINDOW_UPDATE:
+      return "WINDOW_UPDATE";
+    case CONTINUATION:
+      return "CONTINUATION";
+    case ALTSVC:
+      return "ALTSVC";
+    case UNSET:
+      return "UNSET";
+    case UNKNOWN:
+      return "UNKNOWN";
+    default:
+      return "Invalid Http2FrameType";
+  }
+}
+
+// TODO(jamessynge): Switch to using http2/http2_constants.h when ready.
+inline std::ostream& operator<<(std::ostream& out, Http2FrameType v) {
+  return out << Http2FrameTypeToString(v);
+}
+
+// Flag bits in the flag field of the common header of HTTP/2 frames
+// (see https://httpwg.github.io/specs/rfc7540.html#FrameHeader for details on
+// the fixed 9-octet header structure shared by all frames).
+// Flag bits are only valid for specified frame types.
+// TODO(jamessynge): Switch to using http2/http2_constants.h when ready.
+enum Http2HeaderFlag {
+  NO_FLAGS = 0,
+
+  END_STREAM_FLAG = 0x1,
+  ACK_FLAG = 0x1,
+  END_HEADERS_FLAG = 0x4,
+  PADDED_FLAG = 0x8,
+  PRIORITY_FLAG = 0x20,
+};
+
+// Returns name of frame type.
+// TODO(jamessynge): Switch to using http2/http2_constants.h when ready.
+const char* Http2FrameTypeToString(Http2FrameType v);
+
+void SpdyDeframerVisitorInterface::OnPingAck(
+    std::unique_ptr<SpdyPingIR> frame) {
+  OnPing(std::move(frame));
+}
+
+void SpdyDeframerVisitorInterface::OnSettingsAck(
+    std::unique_ptr<SpdySettingsIR> frame) {
+  OnSettings(std::move(frame), nullptr);
+}
+
+class SpdyTestDeframerImpl : public SpdyTestDeframer,
+                             public SpdyHeadersHandlerInterface {
+ public:
+  explicit SpdyTestDeframerImpl(
+      std::unique_ptr<SpdyDeframerVisitorInterface> listener)
+      : listener_(std::move(listener)) {
+    CHECK(listener_ != nullptr);
+  }
+  SpdyTestDeframerImpl(const SpdyTestDeframerImpl&) = delete;
+  SpdyTestDeframerImpl& operator=(const SpdyTestDeframerImpl&) = delete;
+  ~SpdyTestDeframerImpl() override = default;
+
+  bool AtFrameEnd() override;
+
+  // Callbacks defined in SpdyFramerVisitorInterface.  These are in the
+  // alphabetical order for ease of navigation, and are not in same order
+  // as in SpdyFramerVisitorInterface.
+  void OnAltSvc(SpdyStreamId stream_id,
+                SpdyStringPiece origin,
+                const SpdyAltSvcWireFormat::AlternativeServiceVector&
+                    altsvc_vector) override;
+  void OnContinuation(SpdyStreamId stream_id, bool end) override;
+  SpdyHeadersHandlerInterface* OnHeaderFrameStart(
+      SpdyStreamId stream_id) override;
+  void OnHeaderFrameEnd(SpdyStreamId stream_id) override;
+  void OnDataFrameHeader(SpdyStreamId stream_id,
+                         size_t length,
+                         bool fin) override;
+  void OnError(http2::Http2DecoderAdapter::SpdyFramerError error) override;
+  void OnGoAway(SpdyStreamId last_accepted_stream_id,
+                SpdyErrorCode error_code) override;
+  bool OnGoAwayFrameData(const char* goaway_data, size_t len) override;
+  void OnHeaders(SpdyStreamId stream_id,
+                 bool has_priority,
+                 int weight,
+                 SpdyStreamId parent_stream_id,
+                 bool exclusive,
+                 bool fin,
+                 bool end) override;
+  void OnPing(SpdyPingId unique_id, bool is_ack) override;
+  void OnPriority(SpdyStreamId stream_id,
+                  SpdyStreamId parent_stream_id,
+                  int weight,
+                  bool exclusive) override;
+  void OnPushPromise(SpdyStreamId stream_id,
+                     SpdyStreamId promised_stream_id,
+                     bool end) override;
+  void OnRstStream(SpdyStreamId stream_id, SpdyErrorCode error_code) override;
+  void OnSetting(SpdySettingsId id, uint32_t value) override;
+  void OnSettings() override;
+  void OnSettingsAck() override;
+  void OnSettingsEnd() override;
+  void OnStreamFrameData(SpdyStreamId stream_id,
+                         const char* data,
+                         size_t len) override;
+  void OnStreamEnd(SpdyStreamId stream_id) override;
+  void OnStreamPadLength(SpdyStreamId stream_id, size_t value) override;
+  void OnStreamPadding(SpdyStreamId stream_id, size_t len) override;
+  bool OnUnknownFrame(SpdyStreamId stream_id, uint8_t frame_type) override;
+  void OnWindowUpdate(SpdyStreamId stream_id, int delta_window_size) override;
+
+  // Callbacks defined in SpdyHeadersHandlerInterface.
+
+  void OnHeaderBlockStart() override;
+  void OnHeader(SpdyStringPiece key, SpdyStringPiece value) override;
+  void OnHeaderBlockEnd(size_t header_bytes_parsed,
+                        size_t compressed_header_bytes_parsed) override;
+
+ protected:
+  void AtDataEnd();
+  void AtGoAwayEnd();
+  void AtHeadersEnd();
+  void AtPushPromiseEnd();
+
+  // Per-physical frame state.
+  // Frame type of the frame currently being processed.
+  Http2FrameType frame_type_ = UNSET;
+  // Stream id of the frame currently being processed.
+  SpdyStreamId stream_id_;
+  // Did the most recent frame header include the END_HEADERS flag?
+  bool end_ = false;
+  // Did the most recent frame header include the ack flag?
+  bool ack_ = false;
+
+  // Per-HPACK block state. Only valid while processing a HEADERS or
+  // PUSH_PROMISE frame, and its CONTINUATION frames.
+  // Did the most recent HEADERS or PUSH_PROMISE include the END_STREAM flag?
+  // Note that this does not necessarily indicate that the current frame is
+  // the last frame for the stream (may be followed by CONTINUATION frames,
+  // may only half close).
+  bool fin_ = false;
+  bool got_hpack_end_ = false;
+
+  std::unique_ptr<SpdyString> data_;
+
+  // Total length of the data frame.
+  size_t data_len_ = 0;
+
+  // Amount of skipped padding (i.e. total length of padding, including Pad
+  // Length field).
+  size_t padding_len_ = 0;
+
+  std::unique_ptr<SpdyString> goaway_description_;
+  std::unique_ptr<StringPairVector> headers_;
+  std::unique_ptr<SettingVector> settings_;
+  std::unique_ptr<TestHeadersHandler> headers_handler_;
+
+  std::unique_ptr<SpdyGoAwayIR> goaway_ir_;
+  std::unique_ptr<SpdyHeadersIR> headers_ir_;
+  std::unique_ptr<SpdyPushPromiseIR> push_promise_ir_;
+  std::unique_ptr<SpdySettingsIR> settings_ir_;
+
+ private:
+  std::unique_ptr<SpdyDeframerVisitorInterface> listener_;
+};
+
+// static
+std::unique_ptr<SpdyTestDeframer> SpdyTestDeframer::CreateConverter(
+    std::unique_ptr<SpdyDeframerVisitorInterface> listener) {
+  return SpdyMakeUnique<SpdyTestDeframerImpl>(std::move(listener));
+}
+
+void SpdyTestDeframerImpl::AtDataEnd() {
+  DVLOG(1) << "AtDataEnd";
+  CHECK_EQ(data_len_, padding_len_ + data_->size());
+  auto ptr = SpdyMakeUnique<SpdyDataIR>(stream_id_, std::move(*data_));
+  CHECK_EQ(0u, data_->size());
+  data_.reset();
+
+  CHECK_LE(0u, padding_len_);
+  CHECK_LE(padding_len_, 256u);
+  if (padding_len_ > 0) {
+    ptr->set_padding_len(padding_len_);
+  }
+  padding_len_ = 0;
+
+  ptr->set_fin(fin_);
+  listener_->OnData(std::move(ptr));
+  frame_type_ = UNSET;
+  fin_ = false;
+  data_len_ = 0;
+}
+
+void SpdyTestDeframerImpl::AtGoAwayEnd() {
+  DVLOG(1) << "AtDataEnd";
+  CHECK_EQ(frame_type_, GOAWAY);
+  if (HTTP2_DIE_IF_NULL(goaway_description_)->empty()) {
+    listener_->OnGoAway(std::move(goaway_ir_));
+  } else {
+    listener_->OnGoAway(SpdyMakeUnique<SpdyGoAwayIR>(
+        goaway_ir_->last_good_stream_id(), goaway_ir_->error_code(),
+        std::move(*goaway_description_)));
+    CHECK_EQ(0u, goaway_description_->size());
+  }
+  goaway_description_.reset();
+  goaway_ir_.reset();
+  frame_type_ = UNSET;
+}
+
+void SpdyTestDeframerImpl::AtHeadersEnd() {
+  DVLOG(1) << "AtDataEnd";
+  CHECK(frame_type_ == HEADERS || frame_type_ == CONTINUATION)
+      << "   frame_type_=" << Http2FrameTypeToString(frame_type_);
+  CHECK(end_) << "   frame_type_=" << Http2FrameTypeToString(frame_type_);
+  CHECK(got_hpack_end_);
+
+  CHECK(headers_ir_ != nullptr);
+  CHECK(headers_ != nullptr);
+  CHECK(headers_handler_ != nullptr);
+
+  CHECK_LE(0u, padding_len_);
+  CHECK_LE(padding_len_, 256u);
+  if (padding_len_ > 0) {
+    headers_ir_->set_padding_len(padding_len_);
+  }
+  padding_len_ = 0;
+
+  headers_ir_->set_header_block(headers_handler_->decoded_block().Clone());
+  headers_handler_.reset();
+  listener_->OnHeaders(std::move(headers_ir_), std::move(headers_));
+
+  frame_type_ = UNSET;
+  fin_ = false;
+  end_ = false;
+  got_hpack_end_ = false;
+}
+
+void SpdyTestDeframerImpl::AtPushPromiseEnd() {
+  DVLOG(1) << "AtDataEnd";
+  CHECK(frame_type_ == PUSH_PROMISE || frame_type_ == CONTINUATION)
+      << "   frame_type_=" << Http2FrameTypeToString(frame_type_);
+  CHECK(end_) << "   frame_type_=" << Http2FrameTypeToString(frame_type_);
+
+  CHECK(push_promise_ir_ != nullptr);
+  CHECK(headers_ != nullptr);
+  CHECK(headers_handler_ != nullptr);
+
+  CHECK_EQ(headers_ir_.get(), nullptr);
+
+  CHECK_LE(0u, padding_len_);
+  CHECK_LE(padding_len_, 256u);
+  if (padding_len_ > 0) {
+    push_promise_ir_->set_padding_len(padding_len_);
+  }
+  padding_len_ = 0;
+
+  push_promise_ir_->set_header_block(headers_handler_->decoded_block().Clone());
+  headers_handler_.reset();
+  listener_->OnPushPromise(std::move(push_promise_ir_), std::move(headers_));
+
+  frame_type_ = UNSET;
+  end_ = false;
+}
+
+bool SpdyTestDeframerImpl::AtFrameEnd() {
+  bool incomplete_logical_header = false;
+  // The caller says that the SpdyFrame has reached the end of the frame,
+  // so if we have any accumulated data, flush it.
+  switch (frame_type_) {
+    case DATA:
+      AtDataEnd();
+      break;
+
+    case GOAWAY:
+      AtGoAwayEnd();
+      break;
+
+    case HEADERS:
+      if (end_) {
+        AtHeadersEnd();
+      } else {
+        incomplete_logical_header = true;
+      }
+      break;
+
+    case PUSH_PROMISE:
+      if (end_) {
+        AtPushPromiseEnd();
+      } else {
+        incomplete_logical_header = true;
+      }
+      break;
+
+    case CONTINUATION:
+      if (end_) {
+        if (headers_ir_) {
+          AtHeadersEnd();
+        } else if (push_promise_ir_) {
+          AtPushPromiseEnd();
+        } else {
+          LOG(FATAL) << "Where is the SpdyFrameIR for the headers!";
+        }
+      } else {
+        incomplete_logical_header = true;
+      }
+      break;
+
+    case UNSET:
+      // Except for the frame types above, the others don't leave any record
+      // in the state of this object. Make sure nothing got left by accident.
+      CHECK_EQ(data_.get(), nullptr);
+      CHECK_EQ(goaway_description_.get(), nullptr);
+      CHECK_EQ(goaway_ir_.get(), nullptr);
+      CHECK_EQ(headers_.get(), nullptr);
+      CHECK_EQ(headers_handler_.get(), nullptr);
+      CHECK_EQ(headers_ir_.get(), nullptr);
+      CHECK_EQ(push_promise_ir_.get(), nullptr);
+      CHECK_EQ(settings_.get(), nullptr);
+      CHECK_EQ(settings_ir_.get(), nullptr);
+      break;
+
+    default:
+      SPDY_BUG << "Expected UNSET, instead frame_type_==" << frame_type_;
+      return false;
+  }
+  frame_type_ = UNSET;
+  stream_id_ = 0;
+  end_ = false;
+  ack_ = false;
+  if (!incomplete_logical_header) {
+    fin_ = false;
+  }
+  return true;
+}
+
+// Overridden methods from SpdyFramerVisitorInterface in alpha order...
+
+void SpdyTestDeframerImpl::OnAltSvc(
+    SpdyStreamId stream_id,
+    SpdyStringPiece origin,
+    const SpdyAltSvcWireFormat::AlternativeServiceVector& altsvc_vector) {
+  DVLOG(1) << "OnAltSvc stream_id: " << stream_id;
+  CHECK_EQ(frame_type_, UNSET)
+      << "   frame_type_=" << Http2FrameTypeToString(frame_type_);
+  CHECK_GT(stream_id, 0u);
+  auto ptr = SpdyMakeUnique<SpdyAltSvcIR>(stream_id);
+  ptr->set_origin(SpdyString(origin));
+  for (auto& altsvc : altsvc_vector) {
+    ptr->add_altsvc(altsvc);
+  }
+  listener_->OnAltSvc(std::move(ptr));
+}
+
+// A CONTINUATION frame contains a Header Block Fragment, and immediately
+// follows another frame that contains a Header Block Fragment (HEADERS,
+// PUSH_PROMISE or CONTINUATION). The last such frame has the END flag set.
+// SpdyFramer ensures that the behavior is correct before calling the visitor.
+void SpdyTestDeframerImpl::OnContinuation(SpdyStreamId stream_id, bool end) {
+  DVLOG(1) << "OnContinuation stream_id: " << stream_id;
+  CHECK_EQ(frame_type_, UNSET)
+      << "   frame_type_=" << Http2FrameTypeToString(frame_type_);
+  CHECK_GT(stream_id, 0u);
+  CHECK_NE(nullptr, headers_.get());
+  frame_type_ = CONTINUATION;
+
+  stream_id_ = stream_id;
+  end_ = end;
+}
+
+// Note that length includes the padding length (0 to 256, when the optional
+// padding length field is counted). Padding comes after the payload, both
+// for DATA frames and for control frames.
+void SpdyTestDeframerImpl::OnDataFrameHeader(SpdyStreamId stream_id,
+                                             size_t length,
+                                             bool fin) {
+  DVLOG(1) << "OnDataFrameHeader stream_id: " << stream_id;
+  CHECK_EQ(frame_type_, UNSET)
+      << "   frame_type_=" << Http2FrameTypeToString(frame_type_);
+  CHECK_GT(stream_id, 0u);
+  CHECK_EQ(data_.get(), nullptr);
+  frame_type_ = DATA;
+
+  stream_id_ = stream_id;
+  fin_ = fin;
+  data_len_ = length;
+  data_ = SpdyMakeUnique<SpdyString>();
+}
+
+// The SpdyFramer will not process any more data at this point.
+void SpdyTestDeframerImpl::OnError(
+    http2::Http2DecoderAdapter::SpdyFramerError error) {
+  DVLOG(1) << "SpdyFramer detected an error in the stream: "
+           << http2::Http2DecoderAdapter::SpdyFramerErrorToString(error)
+           << "     frame_type_: " << Http2FrameTypeToString(frame_type_);
+  listener_->OnError(error, this);
+}
+
+// Received a GOAWAY frame from the peer. The last stream id it accepted from us
+// is |last_accepted_stream_id|. |status| is a protocol defined error code.
+// The frame may also contain data. After this OnGoAwayFrameData will be called
+// for any non-zero amount of data, and after that it will be called with len==0
+// to indicate the end of the GOAWAY frame.
+void SpdyTestDeframerImpl::OnGoAway(SpdyStreamId last_good_stream_id,
+                                    SpdyErrorCode error_code) {
+  DVLOG(1) << "OnGoAway last_good_stream_id: " << last_good_stream_id
+           << "     error code: " << error_code;
+  CHECK_EQ(frame_type_, UNSET)
+      << "   frame_type_=" << Http2FrameTypeToString(frame_type_);
+  frame_type_ = GOAWAY;
+  goaway_ir_ =
+      SpdyMakeUnique<SpdyGoAwayIR>(last_good_stream_id, error_code, "");
+  goaway_description_ = SpdyMakeUnique<SpdyString>();
+}
+
+// If len==0 then we've reached the end of the GOAWAY frame.
+bool SpdyTestDeframerImpl::OnGoAwayFrameData(const char* goaway_data,
+                                             size_t len) {
+  DVLOG(1) << "OnGoAwayFrameData";
+  CHECK_EQ(frame_type_, GOAWAY)
+      << "   frame_type_=" << Http2FrameTypeToString(frame_type_);
+  CHECK(goaway_description_ != nullptr);
+  goaway_description_->append(goaway_data, len);
+  return true;
+}
+
+SpdyHeadersHandlerInterface* SpdyTestDeframerImpl::OnHeaderFrameStart(
+    SpdyStreamId stream_id) {
+  return this;
+}
+
+void SpdyTestDeframerImpl::OnHeaderFrameEnd(SpdyStreamId stream_id) {
+  DVLOG(1) << "OnHeaderFrameEnd stream_id: " << stream_id;
+}
+
+// Received the fixed portion of a HEADERS frame. Called before the variable
+// length (including zero length) Header Block Fragment is processed. If fin
+// is true then there will be no DATA or trailing HEADERS after this HEADERS
+// frame.
+// If end is true, then there will be no CONTINUATION frame(s) following this
+// frame; else if true then there will be CONTINATION frames(s) immediately
+// following this frame, terminated by a CONTINUATION frame with end==true.
+void SpdyTestDeframerImpl::OnHeaders(SpdyStreamId stream_id,
+                                     bool has_priority,
+                                     int weight,
+                                     SpdyStreamId parent_stream_id,
+                                     bool exclusive,
+                                     bool fin,
+                                     bool end) {
+  DVLOG(1) << "OnHeaders stream_id: " << stream_id;
+  CHECK_EQ(frame_type_, UNSET)
+      << "   frame_type_=" << Http2FrameTypeToString(frame_type_);
+  CHECK_GT(stream_id, 0u);
+  frame_type_ = HEADERS;
+
+  stream_id_ = stream_id;
+  fin_ = fin;
+  end_ = end;
+
+  headers_ = SpdyMakeUnique<StringPairVector>();
+  headers_handler_ = SpdyMakeUnique<TestHeadersHandler>();
+  headers_ir_ = SpdyMakeUnique<SpdyHeadersIR>(stream_id);
+  headers_ir_->set_fin(fin);
+  if (has_priority) {
+    headers_ir_->set_has_priority(true);
+    headers_ir_->set_weight(weight);
+    headers_ir_->set_parent_stream_id(parent_stream_id);
+    headers_ir_->set_exclusive(exclusive);
+  }
+}
+
+// The HTTP/2 protocol refers to the payload, |unique_id| here, as 8 octets of
+// opaque data that is to be echoed back to the sender, with the ACK bit added.
+// It isn't defined as a counter,
+// or frame id, as the SpdyPingId naming might imply.
+// Responding to a PING is supposed to be at the highest priority.
+void SpdyTestDeframerImpl::OnPing(uint64_t unique_id, bool is_ack) {
+  DVLOG(1) << "OnPing unique_id: " << unique_id
+           << "      is_ack: " << (is_ack ? "true" : "false");
+  CHECK_EQ(frame_type_, UNSET)
+      << "   frame_type_=" << Http2FrameTypeToString(frame_type_);
+  auto ptr = SpdyMakeUnique<SpdyPingIR>(unique_id);
+  if (is_ack) {
+    ptr->set_is_ack(is_ack);
+    listener_->OnPingAck(std::move(ptr));
+  } else {
+    listener_->OnPing(std::move(ptr));
+  }
+}
+
+void SpdyTestDeframerImpl::OnPriority(SpdyStreamId stream_id,
+                                      SpdyStreamId parent_stream_id,
+                                      int weight,
+                                      bool exclusive) {
+  DVLOG(1) << "OnPriority stream_id: " << stream_id;
+  CHECK_EQ(frame_type_, UNSET)
+      << "   frame_type_=" << Http2FrameTypeToString(frame_type_);
+  CHECK_GT(stream_id, 0u);
+
+  listener_->OnPriority(SpdyMakeUnique<SpdyPriorityIR>(
+      stream_id, parent_stream_id, weight, exclusive));
+}
+
+void SpdyTestDeframerImpl::OnPushPromise(SpdyStreamId stream_id,
+                                         SpdyStreamId promised_stream_id,
+                                         bool end) {
+  DVLOG(1) << "OnPushPromise stream_id: " << stream_id;
+  CHECK_EQ(frame_type_, UNSET)
+      << "   frame_type_=" << Http2FrameTypeToString(frame_type_);
+  CHECK_GT(stream_id, 0u);
+
+  frame_type_ = PUSH_PROMISE;
+  stream_id_ = stream_id;
+  end_ = end;
+
+  headers_ = SpdyMakeUnique<StringPairVector>();
+  headers_handler_ = SpdyMakeUnique<TestHeadersHandler>();
+  push_promise_ir_ =
+      SpdyMakeUnique<SpdyPushPromiseIR>(stream_id, promised_stream_id);
+}
+
+// Closes the specified stream. After this the sender may still send PRIORITY
+// frames for this stream, which we can ignore.
+void SpdyTestDeframerImpl::OnRstStream(SpdyStreamId stream_id,
+                                       SpdyErrorCode error_code) {
+  DVLOG(1) << "OnRstStream stream_id: " << stream_id
+           << "     error code: " << error_code;
+  CHECK_EQ(frame_type_, UNSET)
+      << "   frame_type_=" << Http2FrameTypeToString(frame_type_);
+  CHECK_GT(stream_id, 0u);
+
+  listener_->OnRstStream(
+      SpdyMakeUnique<SpdyRstStreamIR>(stream_id, error_code));
+}
+
+// Called for an individual setting. There is no negotiation; the sender is
+// stating the value that the sender is using.
+void SpdyTestDeframerImpl::OnSetting(SpdySettingsId id, uint32_t value) {
+  DVLOG(1) << "OnSetting id: " << id << std::hex << "    value: " << value;
+  CHECK_EQ(frame_type_, SETTINGS)
+      << "   frame_type_=" << Http2FrameTypeToString(frame_type_);
+  CHECK(settings_ != nullptr);
+  SpdyKnownSettingsId known_id;
+  if (ParseSettingsId(id, &known_id)) {
+    settings_->push_back(std::make_pair(known_id, value));
+    settings_ir_->AddSetting(known_id, value);
+  }
+}
+
+// Called at the start of a SETTINGS frame with setting entries, but not the
+// (required) ACK of a SETTINGS frame. There is no stream_id because
+// the settings apply to the entire connection, not to an individual stream.
+void SpdyTestDeframerImpl::OnSettings() {
+  DVLOG(1) << "OnSettings";
+  CHECK_EQ(frame_type_, UNSET)
+      << "   frame_type_=" << Http2FrameTypeToString(frame_type_);
+  CHECK_EQ(nullptr, settings_ir_.get());
+  CHECK_EQ(nullptr, settings_.get());
+  frame_type_ = SETTINGS;
+  ack_ = false;
+
+  settings_ = SpdyMakeUnique<SettingVector>();
+  settings_ir_ = SpdyMakeUnique<SpdySettingsIR>();
+}
+
+void SpdyTestDeframerImpl::OnSettingsAck() {
+  DVLOG(1) << "OnSettingsAck";
+  CHECK_EQ(frame_type_, UNSET)
+      << "   frame_type_=" << Http2FrameTypeToString(frame_type_);
+  auto ptr = SpdyMakeUnique<SpdySettingsIR>();
+  ptr->set_is_ack(true);
+  listener_->OnSettingsAck(std::move(ptr));
+}
+
+void SpdyTestDeframerImpl::OnSettingsEnd() {
+  DVLOG(1) << "OnSettingsEnd";
+  CHECK_EQ(frame_type_, SETTINGS)
+      << "   frame_type_=" << Http2FrameTypeToString(frame_type_);
+  CHECK(!ack_);
+  CHECK_NE(nullptr, settings_ir_.get());
+  CHECK_NE(nullptr, settings_.get());
+  listener_->OnSettings(std::move(settings_ir_), std::move(settings_));
+  frame_type_ = UNSET;
+}
+
+// Called for a zero length DATA frame with the END_STREAM flag set, or at the
+// end a complete HPACK block (and its padding) that started with a HEADERS
+// frame with the END_STREAM flag set. Doesn't apply to PUSH_PROMISE frames
+// because they don't have END_STREAM flags.
+void SpdyTestDeframerImpl::OnStreamEnd(SpdyStreamId stream_id) {
+  DVLOG(1) << "OnStreamEnd stream_id: " << stream_id;
+  CHECK_EQ(stream_id_, stream_id);
+  CHECK(frame_type_ == DATA || frame_type_ == HEADERS ||
+        frame_type_ == CONTINUATION)
+      << "   frame_type_=" << Http2FrameTypeToString(frame_type_);
+  CHECK(fin_);
+}
+
+// The data arg points into the non-padding payload of a DATA frame.
+// This must be a DATA frame (i.e. this method will not be
+// called for HEADERS or CONTINUATION frames).
+// This method may be called multiple times for a single DATA frame, depending
+// upon buffer boundaries.
+void SpdyTestDeframerImpl::OnStreamFrameData(SpdyStreamId stream_id,
+                                             const char* data,
+                                             size_t len) {
+  DVLOG(1) << "OnStreamFrameData stream_id: " << stream_id
+           << "    len: " << len;
+  CHECK_EQ(stream_id_, stream_id);
+  CHECK_EQ(frame_type_, DATA);
+  data_->append(data, len);
+}
+
+// Called when receiving the padding length field at the start of the DATA frame
+// payload. value will be in the range 0 to 255.
+void SpdyTestDeframerImpl::OnStreamPadLength(SpdyStreamId stream_id,
+                                             size_t value) {
+  DVLOG(1) << "OnStreamPadding stream_id: " << stream_id
+           << "    value: " << value;
+  CHECK(frame_type_ == DATA || frame_type_ == HEADERS ||
+        frame_type_ == PUSH_PROMISE)
+      << "   frame_type_=" << Http2FrameTypeToString(frame_type_);
+  CHECK_EQ(stream_id_, stream_id);
+  CHECK_GE(255u, value);
+  // Count the padding length byte against total padding.
+  padding_len_ += 1;
+  CHECK_EQ(1u, padding_len_);
+}
+
+// Called when padding is skipped over at the end of the DATA frame. len will
+// be in the range 1 to 255.
+void SpdyTestDeframerImpl::OnStreamPadding(SpdyStreamId stream_id, size_t len) {
+  DVLOG(1) << "OnStreamPadding stream_id: " << stream_id << "    len: " << len;
+  CHECK(frame_type_ == DATA || frame_type_ == HEADERS ||
+        frame_type_ == PUSH_PROMISE)
+      << "   frame_type_=" << Http2FrameTypeToString(frame_type_);
+  CHECK_EQ(stream_id_, stream_id);
+  CHECK_LE(1u, len);
+  CHECK_GE(255u, len);
+  padding_len_ += len;
+  CHECK_LE(padding_len_, 256u) << "len=" << len;
+}
+
+// WINDOW_UPDATE is supposed to be hop-by-hop, according to the spec.
+// stream_id is 0 if the update applies to the connection, else stream_id
+// will be the id of a stream previously seen, which maybe half or fully
+// closed.
+void SpdyTestDeframerImpl::OnWindowUpdate(SpdyStreamId stream_id,
+                                          int delta_window_size) {
+  DVLOG(1) << "OnWindowUpdate stream_id: " << stream_id
+           << "    delta_window_size: " << delta_window_size;
+  CHECK_EQ(frame_type_, UNSET)
+      << "   frame_type_=" << Http2FrameTypeToString(frame_type_);
+  CHECK_NE(0, delta_window_size);
+
+  listener_->OnWindowUpdate(
+      SpdyMakeUnique<SpdyWindowUpdateIR>(stream_id, delta_window_size));
+}
+
+// Return true to indicate that the stream_id is valid; if not valid then
+// SpdyFramer considers the connection corrupted. Requires keeping track
+// of the set of currently open streams. For now we'll assume that unknown
+// frame types are unsupported.
+bool SpdyTestDeframerImpl::OnUnknownFrame(SpdyStreamId stream_id,
+                                          uint8_t frame_type) {
+  DVLOG(1) << "OnAltSvc stream_id: " << stream_id;
+  CHECK_EQ(frame_type_, UNSET)
+      << "   frame_type_=" << Http2FrameTypeToString(frame_type_);
+  frame_type_ = UNKNOWN;
+
+  stream_id_ = stream_id;
+  return false;
+}
+
+// Callbacks defined in SpdyHeadersHandlerInterface.
+
+void SpdyTestDeframerImpl::OnHeaderBlockStart() {
+  CHECK(frame_type_ == HEADERS || frame_type_ == PUSH_PROMISE)
+      << "   frame_type_=" << Http2FrameTypeToString(frame_type_);
+  CHECK(headers_ != nullptr);
+  CHECK_EQ(0u, headers_->size());
+  got_hpack_end_ = false;
+}
+
+void SpdyTestDeframerImpl::OnHeader(SpdyStringPiece key,
+                                    SpdyStringPiece value) {
+  CHECK(frame_type_ == HEADERS || frame_type_ == CONTINUATION ||
+        frame_type_ == PUSH_PROMISE)
+      << "   frame_type_=" << Http2FrameTypeToString(frame_type_);
+  CHECK(!got_hpack_end_);
+  HTTP2_DIE_IF_NULL(headers_)->emplace_back(SpdyString(key), SpdyString(value));
+  HTTP2_DIE_IF_NULL(headers_handler_)->OnHeader(key, value);
+}
+
+void SpdyTestDeframerImpl::OnHeaderBlockEnd(
+    size_t /* header_bytes_parsed */,
+    size_t /* compressed_header_bytes_parsed */) {
+  CHECK(headers_ != nullptr);
+  CHECK(frame_type_ == HEADERS || frame_type_ == CONTINUATION ||
+        frame_type_ == PUSH_PROMISE)
+      << "   frame_type_=" << Http2FrameTypeToString(frame_type_);
+  CHECK(end_);
+  CHECK(!got_hpack_end_);
+  got_hpack_end_ = true;
+}
+
+class LoggingSpdyDeframerDelegate : public SpdyDeframerVisitorInterface {
+ public:
+  explicit LoggingSpdyDeframerDelegate(
+      std::unique_ptr<SpdyDeframerVisitorInterface> wrapped)
+      : wrapped_(std::move(wrapped)) {
+    if (!wrapped_) {
+      wrapped_ = SpdyMakeUnique<SpdyDeframerVisitorInterface>();
+    }
+  }
+  ~LoggingSpdyDeframerDelegate() override = default;
+
+  void OnAltSvc(std::unique_ptr<SpdyAltSvcIR> frame) override {
+    DVLOG(1) << "LoggingSpdyDeframerDelegate::OnAltSvc";
+    wrapped_->OnAltSvc(std::move(frame));
+  }
+  void OnData(std::unique_ptr<SpdyDataIR> frame) override {
+    DVLOG(1) << "LoggingSpdyDeframerDelegate::OnData";
+    wrapped_->OnData(std::move(frame));
+  }
+  void OnGoAway(std::unique_ptr<SpdyGoAwayIR> frame) override {
+    DVLOG(1) << "LoggingSpdyDeframerDelegate::OnGoAway";
+    wrapped_->OnGoAway(std::move(frame));
+  }
+
+  // SpdyHeadersIR and SpdyPushPromiseIR each has a SpdyHeaderBlock which
+  // significantly modifies the headers, so the actual header entries (name
+  // and value strings) are provided in a vector.
+  void OnHeaders(std::unique_ptr<SpdyHeadersIR> frame,
+                 std::unique_ptr<StringPairVector> headers) override {
+    DVLOG(1) << "LoggingSpdyDeframerDelegate::OnHeaders";
+    wrapped_->OnHeaders(std::move(frame), std::move(headers));
+  }
+
+  void OnPing(std::unique_ptr<SpdyPingIR> frame) override {
+    DVLOG(1) << "LoggingSpdyDeframerDelegate::OnPing";
+    wrapped_->OnPing(std::move(frame));
+  }
+  void OnPingAck(std::unique_ptr<SpdyPingIR> frame) override {
+    DVLOG(1) << "LoggingSpdyDeframerDelegate::OnPingAck";
+    wrapped_->OnPingAck(std::move(frame));
+  }
+
+  void OnPriority(std::unique_ptr<SpdyPriorityIR> frame) override {
+    DVLOG(1) << "LoggingSpdyDeframerDelegate::OnPriority";
+    wrapped_->OnPriority(std::move(frame));
+  }
+
+  // SpdyHeadersIR and SpdyPushPromiseIR each has a SpdyHeaderBlock which
+  // significantly modifies the headers, so the actual header entries (name
+  // and value strings) are provided in a vector.
+  void OnPushPromise(std::unique_ptr<SpdyPushPromiseIR> frame,
+                     std::unique_ptr<StringPairVector> headers) override {
+    DVLOG(1) << "LoggingSpdyDeframerDelegate::OnPushPromise";
+    wrapped_->OnPushPromise(std::move(frame), std::move(headers));
+  }
+
+  void OnRstStream(std::unique_ptr<SpdyRstStreamIR> frame) override {
+    DVLOG(1) << "LoggingSpdyDeframerDelegate::OnRstStream";
+    wrapped_->OnRstStream(std::move(frame));
+  }
+
+  // SpdySettingsIR has a map for settings, so loses info about the order of
+  // settings, and whether the same setting appeared more than once, so the
+  // the actual settings (parameter and value) are provided in a vector.
+  void OnSettings(std::unique_ptr<SpdySettingsIR> frame,
+                  std::unique_ptr<SettingVector> settings) override {
+    DVLOG(1) << "LoggingSpdyDeframerDelegate::OnSettings";
+    wrapped_->OnSettings(std::move(frame), std::move(settings));
+  }
+
+  // A settings frame with an ACK has no content, but for uniformity passing
+  // a frame with the ACK flag set.
+  void OnSettingsAck(std::unique_ptr<SpdySettingsIR> frame) override {
+    DVLOG(1) << "LoggingSpdyDeframerDelegate::OnSettingsAck";
+    wrapped_->OnSettingsAck(std::move(frame));
+  }
+
+  void OnWindowUpdate(std::unique_ptr<SpdyWindowUpdateIR> frame) override {
+    DVLOG(1) << "LoggingSpdyDeframerDelegate::OnWindowUpdate";
+    wrapped_->OnWindowUpdate(std::move(frame));
+  }
+
+  // The SpdyFramer will not process any more data at this point.
+  void OnError(http2::Http2DecoderAdapter::SpdyFramerError error,
+               SpdyTestDeframer* deframer) override {
+    DVLOG(1) << "LoggingSpdyDeframerDelegate::OnError";
+    wrapped_->OnError(error, deframer);
+  }
+
+ private:
+  std::unique_ptr<SpdyDeframerVisitorInterface> wrapped_;
+};
+
+// static
+std::unique_ptr<SpdyDeframerVisitorInterface>
+SpdyDeframerVisitorInterface::LogBeforeVisiting(
+    std::unique_ptr<SpdyDeframerVisitorInterface> wrapped_listener) {
+  return SpdyMakeUnique<LoggingSpdyDeframerDelegate>(
+      std::move(wrapped_listener));
+}
+
+CollectedFrame::CollectedFrame() = default;
+
+CollectedFrame::CollectedFrame(CollectedFrame&& other)
+    : frame_ir(std::move(other.frame_ir)),
+      headers(std::move(other.headers)),
+      settings(std::move(other.settings)),
+      error_reported(other.error_reported) {}
+
+CollectedFrame::~CollectedFrame() = default;
+
+CollectedFrame& CollectedFrame::operator=(CollectedFrame&& other) {
+  frame_ir = std::move(other.frame_ir);
+  headers = std::move(other.headers);
+  settings = std::move(other.settings);
+  error_reported = other.error_reported;
+  return *this;
+}
+
+AssertionResult CollectedFrame::VerifyHasHeaders(
+    const StringPairVector& expected_headers) const {
+  VERIFY_NE(headers.get(), nullptr);
+  VERIFY_THAT(*headers, ::testing::ContainerEq(expected_headers));
+  return AssertionSuccess();
+}
+
+AssertionResult CollectedFrame::VerifyHasSettings(
+    const SettingVector& expected_settings) const {
+  VERIFY_NE(settings.get(), nullptr);
+  VERIFY_THAT(*settings, testing::ContainerEq(expected_settings));
+  return AssertionSuccess();
+}
+
+DeframerCallbackCollector::DeframerCallbackCollector(
+    std::vector<CollectedFrame>* collected_frames)
+    : collected_frames_(HTTP2_DIE_IF_NULL(collected_frames)) {}
+
+void DeframerCallbackCollector::OnAltSvc(
+    std::unique_ptr<SpdyAltSvcIR> frame_ir) {
+  CollectedFrame cf;
+  cf.frame_ir = std::move(frame_ir);
+  collected_frames_->push_back(std::move(cf));
+}
+void DeframerCallbackCollector::OnData(std::unique_ptr<SpdyDataIR> frame_ir) {
+  CollectedFrame cf;
+  cf.frame_ir = std::move(frame_ir);
+  collected_frames_->push_back(std::move(cf));
+}
+void DeframerCallbackCollector::OnGoAway(
+    std::unique_ptr<SpdyGoAwayIR> frame_ir) {
+  CollectedFrame cf;
+  cf.frame_ir = std::move(frame_ir);
+  collected_frames_->push_back(std::move(cf));
+}
+
+// SpdyHeadersIR and SpdyPushPromiseIR each has a SpdyHeaderBlock which
+// significantly modifies the headers, so the actual header entries (name
+// and value strings) are provided in a vector.
+void DeframerCallbackCollector::OnHeaders(
+    std::unique_ptr<SpdyHeadersIR> frame_ir,
+    std::unique_ptr<StringPairVector> headers) {
+  CollectedFrame cf;
+  cf.frame_ir = std::move(frame_ir);
+  cf.headers = std::move(headers);
+  collected_frames_->push_back(std::move(cf));
+}
+
+void DeframerCallbackCollector::OnPing(std::unique_ptr<SpdyPingIR> frame_ir) {
+  EXPECT_TRUE(frame_ir && !frame_ir->is_ack());
+  CollectedFrame cf;
+  cf.frame_ir = std::move(frame_ir);
+  collected_frames_->push_back(std::move(cf));
+}
+
+void DeframerCallbackCollector::OnPingAck(
+    std::unique_ptr<SpdyPingIR> frame_ir) {
+  EXPECT_TRUE(frame_ir && frame_ir->is_ack());
+  CollectedFrame cf;
+  cf.frame_ir = std::move(frame_ir);
+  collected_frames_->push_back(std::move(cf));
+}
+
+void DeframerCallbackCollector::OnPriority(
+    std::unique_ptr<SpdyPriorityIR> frame_ir) {
+  CollectedFrame cf;
+  cf.frame_ir = std::move(frame_ir);
+  collected_frames_->push_back(std::move(cf));
+}
+
+// SpdyHeadersIR and SpdyPushPromiseIR each has a SpdyHeaderBlock which
+// significantly modifies the headers, so the actual header entries (name
+// and value strings) are provided in a vector.
+void DeframerCallbackCollector::OnPushPromise(
+    std::unique_ptr<SpdyPushPromiseIR> frame_ir,
+    std::unique_ptr<StringPairVector> headers) {
+  CollectedFrame cf;
+  cf.frame_ir = std::move(frame_ir);
+  cf.headers = std::move(headers);
+  collected_frames_->push_back(std::move(cf));
+}
+
+void DeframerCallbackCollector::OnRstStream(
+    std::unique_ptr<SpdyRstStreamIR> frame_ir) {
+  CollectedFrame cf;
+  cf.frame_ir = std::move(frame_ir);
+  collected_frames_->push_back(std::move(cf));
+}
+
+// SpdySettingsIR has a map for settings, so loses info about the order of
+// settings, and whether the same setting appeared more than once, so the
+// the actual settings (parameter and value) are provided in a vector.
+void DeframerCallbackCollector::OnSettings(
+    std::unique_ptr<SpdySettingsIR> frame_ir,
+    std::unique_ptr<SettingVector> settings) {
+  EXPECT_TRUE(frame_ir && !frame_ir->is_ack());
+  CollectedFrame cf;
+  cf.frame_ir = std::move(frame_ir);
+  cf.settings = std::move(settings);
+  collected_frames_->push_back(std::move(cf));
+}
+
+// A settings frame_ir with an ACK has no content, but for uniformity passing
+// a frame_ir with the ACK flag set.
+void DeframerCallbackCollector::OnSettingsAck(
+    std::unique_ptr<SpdySettingsIR> frame_ir) {
+  EXPECT_TRUE(frame_ir && frame_ir->is_ack());
+  CollectedFrame cf;
+  cf.frame_ir = std::move(frame_ir);
+  collected_frames_->push_back(std::move(cf));
+}
+
+void DeframerCallbackCollector::OnWindowUpdate(
+    std::unique_ptr<SpdyWindowUpdateIR> frame_ir) {
+  CollectedFrame cf;
+  cf.frame_ir = std::move(frame_ir);
+  collected_frames_->push_back(std::move(cf));
+}
+
+// The SpdyFramer will not process any more data at this point.
+void DeframerCallbackCollector::OnError(
+    http2::Http2DecoderAdapter::SpdyFramerError error,
+    SpdyTestDeframer* deframer) {
+  CollectedFrame cf;
+  cf.error_reported = true;
+  collected_frames_->push_back(std::move(cf));
+}
+
+}  // namespace test
+}  // namespace spdy
diff --git a/spdy/core/spdy_deframer_visitor.h b/spdy/core/spdy_deframer_visitor.h
new file mode 100644
index 0000000..50d9987
--- /dev/null
+++ b/spdy/core/spdy_deframer_visitor.h
@@ -0,0 +1,250 @@
+// Copyright 2016 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef QUICHE_SPDY_CORE_SPDY_DEFRAMER_VISITOR_H_
+#define QUICHE_SPDY_CORE_SPDY_DEFRAMER_VISITOR_H_
+
+// Supports testing by converting callbacks to SpdyFramerVisitorInterface into
+// callbacks to SpdyDeframerVisitorInterface, whose arguments are generally
+// SpdyFrameIR instances. This enables a test client or test backend to operate
+// at a level between the low-level callbacks of SpdyFramerVisitorInterface and
+// the much higher level of entire messages (i.e. headers, body, trailers).
+// Where possible the converter (SpdyTestDeframer) tries to preserve information
+// that might be useful to tests (e.g. the order of headers or the amount of
+// padding); the design also aims to allow tests to be concise, ideally
+// supporting gMock style EXPECT_CALL(visitor, OnHeaders(...matchers...))
+// without too much boilerplate.
+//
+// Only supports HTTP/2 for the moment.
+//
+// Example of usage:
+//
+//    SpdyFramer framer(HTTP2);
+//
+//    // Need to call SpdyTestDeframer::AtFrameEnd() after processing each
+//    // frame, so tell SpdyFramer to stop after each.
+//    framer.set_process_single_input_frame(true);
+//
+//    // Need the new OnHeader callbacks.
+//    framer.set_use_new_methods_for_test(true);
+//
+//    // Create your visitor, a subclass of SpdyDeframerVisitorInterface.
+//    // For example, using DeframerCallbackCollector to collect frames:
+//    std::vector<CollectedFrame> collected_frames;
+//    auto your_visitor = SpdyMakeUnique<DeframerCallbackCollector>(
+//        &collected_frames);
+//
+//    // Transfer ownership of your visitor to the converter, which ensures that
+//    // your visitor stays alive while the converter needs to call it.
+//    auto the_deframer = SpdyTestDeframer::CreateConverter(
+//       std::move(your_visitor));
+//
+//    // Tell the framer to notify SpdyTestDeframer of the decoded frame
+//    // details.
+//    framer.set_visitor(the_deframer.get());
+//
+//    // Process frames.
+//    SpdyStringPiece input = ...
+//    while (!input.empty() && !framer.HasError()) {
+//      size_t consumed = framer.ProcessInput(input.data(), input.size());
+//      input.remove_prefix(consumed);
+//      if (framer.state() == SpdyFramer::SPDY_READY_FOR_FRAME) {
+//        the_deframer->AtFrameEnd();
+//      }
+//    }
+//
+//    // Make sure that the correct frames were received. For example:
+//    ASSERT_EQ(collected_frames.size(), 3);
+//
+//    SpdyDataIR expected1(7 /*stream_id*/, "Data Payload");
+//    expected1.set_padding_len(17);
+//    EXPECT_TRUE(collected_frames[0].VerifyEquals(expected1));
+//
+//    // Repeat for the other frames.
+//
+// Note that you could also seed the subclass of SpdyDeframerVisitorInterface
+// with the expected frames, which it would pop-off the list as its expectations
+// are met.
+
+#include <cstdint>
+
+#include <memory>
+#include <type_traits>
+#include <utility>
+#include <vector>
+
+#include "base/logging.h"
+#include "base/macros.h"
+#include "testing/gtest/include/gtest/gtest.h"
+#include "net/third_party/quiche/src/spdy/core/http2_frame_decoder_adapter.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_protocol.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_protocol_test_utils.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_test_utils.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string.h"
+
+namespace spdy {
+namespace test {
+
+// Non-lossy representation of a SETTINGS frame payload.
+typedef std::vector<std::pair<SpdyKnownSettingsId, uint32_t>> SettingVector;
+
+// StringPairVector is used to record information lost by SpdyHeaderBlock, in
+// particular the order of each header entry, though it doesn't expose the
+// inner details of the HPACK block, such as the type of encoding selected
+// for each header entry, nor dynamic table size changes.
+typedef std::pair<SpdyString, SpdyString> StringPair;
+typedef std::vector<StringPair> StringPairVector;
+
+// Forward decl.
+class SpdyTestDeframer;
+
+// Note that this only roughly captures the frames, as padding bytes are lost,
+// continuation frames are combined with their leading HEADERS or PUSH_PROMISE,
+// the details of the HPACK encoding are lost, leaving
+// only the list of header entries (name and value strings). If really helpful,
+// we could add a SpdyRawDeframerVisitorInterface that gets the HPACK bytes,
+// and receives continuation frames. For more info we'd need to improve
+// SpdyFramerVisitorInterface.
+class SpdyDeframerVisitorInterface {
+ public:
+  virtual ~SpdyDeframerVisitorInterface() {}
+
+  // Wrap a visitor in another SpdyDeframerVisitorInterface that will
+  // DVLOG each call, and will then forward the calls to the wrapped visitor
+  // (if provided; nullptr is OK). Takes ownership of the wrapped visitor.
+  static std::unique_ptr<SpdyDeframerVisitorInterface> LogBeforeVisiting(
+      std::unique_ptr<SpdyDeframerVisitorInterface> wrapped_visitor);
+
+  virtual void OnAltSvc(std::unique_ptr<SpdyAltSvcIR> frame) {}
+  virtual void OnData(std::unique_ptr<SpdyDataIR> frame) {}
+  virtual void OnGoAway(std::unique_ptr<SpdyGoAwayIR> frame) {}
+
+  // SpdyHeadersIR and SpdyPushPromiseIR each has a SpdyHeaderBlock which
+  // significantly modifies the headers, so the actual header entries (name
+  // and value strings) are provided in a vector.
+  virtual void OnHeaders(std::unique_ptr<SpdyHeadersIR> frame,
+                         std::unique_ptr<StringPairVector> headers) {}
+
+  virtual void OnPing(std::unique_ptr<SpdyPingIR> frame) {}
+  virtual void OnPingAck(std::unique_ptr<SpdyPingIR> frame);
+  virtual void OnPriority(std::unique_ptr<SpdyPriorityIR> frame) {}
+
+  // SpdyHeadersIR and SpdyPushPromiseIR each has a SpdyHeaderBlock which
+  // significantly modifies the headers, so the actual header entries (name
+  // and value strings) are provided in a vector.
+  virtual void OnPushPromise(std::unique_ptr<SpdyPushPromiseIR> frame,
+                             std::unique_ptr<StringPairVector> headers) {}
+
+  virtual void OnRstStream(std::unique_ptr<SpdyRstStreamIR> frame) {}
+
+  // SpdySettingsIR has a map for settings, so loses info about the order of
+  // settings, and whether the same setting appeared more than once, so the
+  // the actual settings (parameter and value) are provided in a vector.
+  virtual void OnSettings(std::unique_ptr<SpdySettingsIR> frame,
+                          std::unique_ptr<SettingVector> settings) {}
+
+  // A settings frame with an ACK has no content, but for uniformity passing
+  // a frame with the ACK flag set.
+  virtual void OnSettingsAck(std::unique_ptr<SpdySettingsIR> frame);
+
+  virtual void OnWindowUpdate(std::unique_ptr<SpdyWindowUpdateIR> frame) {}
+
+  // The SpdyFramer will not process any more data at this point.
+  virtual void OnError(http2::Http2DecoderAdapter::SpdyFramerError error,
+                       SpdyTestDeframer* deframer) {}
+};
+
+class SpdyTestDeframer : public SpdyFramerVisitorInterface {
+ public:
+  ~SpdyTestDeframer() override {}
+
+  // Creates a SpdyFramerVisitorInterface that builds SpdyFrameIR concrete
+  // instances based on the callbacks it receives; when an entire frame is
+  // decoded/reconstructed it calls the passed in SpdyDeframerVisitorInterface.
+  // Transfers ownership of visitor to the new SpdyTestDeframer, which ensures
+  // that it continues to exist while the SpdyTestDeframer exists.
+  static std::unique_ptr<SpdyTestDeframer> CreateConverter(
+      std::unique_ptr<SpdyDeframerVisitorInterface> visitor);
+
+  // Call to notify the deframer that the SpdyFramer has returned after reaching
+  // the end of decoding a frame. This is used to flush info about some frame
+  // types where we don't get a clear end signal; others are flushed (i.e. the
+  // appropriate call to the SpdyDeframerVisitorInterface method is invoked)
+  // as they're decoded by SpdyFramer and it calls the deframer. See the
+  // example in the comments at the top of this file.
+  virtual bool AtFrameEnd() = 0;
+
+ protected:
+  SpdyTestDeframer() {}
+  SpdyTestDeframer(const SpdyTestDeframer&) = delete;
+  SpdyTestDeframer& operator=(const SpdyTestDeframer&) = delete;
+};
+
+// CollectedFrame holds the result of one call to SpdyDeframerVisitorInterface,
+// as recorded by DeframerCallbackCollector.
+struct CollectedFrame {
+  CollectedFrame();
+  CollectedFrame(CollectedFrame&& other);
+  ~CollectedFrame();
+  CollectedFrame& operator=(CollectedFrame&& other);
+
+  // Compare a SpdyFrameIR sub-class instance, expected_ir, against the
+  // collected SpdyFrameIR.
+  template <class T,
+            typename X =
+                typename std::enable_if<std::is_base_of<SpdyFrameIR, T>::value>>
+  ::testing::AssertionResult VerifyHasFrame(const T& expected_ir) const {
+    return VerifySpdyFrameIREquals(expected_ir, frame_ir.get());
+  }
+
+  // Compare the collected headers against a StringPairVector. Ignores
+  // this->frame_ir.
+  ::testing::AssertionResult VerifyHasHeaders(
+      const StringPairVector& expected_headers) const;
+
+  // Compare the collected settings (parameter and value pairs) against
+  // expected_settings. Ignores this->frame_ir.
+  ::testing::AssertionResult VerifyHasSettings(
+      const SettingVector& expected_settings) const;
+
+  std::unique_ptr<SpdyFrameIR> frame_ir;
+  std::unique_ptr<StringPairVector> headers;
+  std::unique_ptr<SettingVector> settings;
+  bool error_reported = false;
+};
+
+// Creates a CollectedFrame instance for each callback, storing it in the
+// vector provided to the constructor.
+class DeframerCallbackCollector : public SpdyDeframerVisitorInterface {
+ public:
+  explicit DeframerCallbackCollector(
+      std::vector<CollectedFrame>* collected_frames);
+  ~DeframerCallbackCollector() override {}
+
+  void OnAltSvc(std::unique_ptr<SpdyAltSvcIR> frame_ir) override;
+  void OnData(std::unique_ptr<SpdyDataIR> frame_ir) override;
+  void OnGoAway(std::unique_ptr<SpdyGoAwayIR> frame_ir) override;
+  void OnHeaders(std::unique_ptr<SpdyHeadersIR> frame_ir,
+                 std::unique_ptr<StringPairVector> headers) override;
+  void OnPing(std::unique_ptr<SpdyPingIR> frame_ir) override;
+  void OnPingAck(std::unique_ptr<SpdyPingIR> frame_ir) override;
+  void OnPriority(std::unique_ptr<SpdyPriorityIR> frame_ir) override;
+  void OnPushPromise(std::unique_ptr<SpdyPushPromiseIR> frame_ir,
+                     std::unique_ptr<StringPairVector> headers) override;
+  void OnRstStream(std::unique_ptr<SpdyRstStreamIR> frame_ir) override;
+  void OnSettings(std::unique_ptr<SpdySettingsIR> frame_ir,
+                  std::unique_ptr<SettingVector> settings) override;
+  void OnSettingsAck(std::unique_ptr<SpdySettingsIR> frame_ir) override;
+  void OnWindowUpdate(std::unique_ptr<SpdyWindowUpdateIR> frame_ir) override;
+  void OnError(http2::Http2DecoderAdapter::SpdyFramerError error,
+               SpdyTestDeframer* deframer) override;
+
+ private:
+  std::vector<CollectedFrame>* collected_frames_;
+};
+
+}  // namespace test
+}  // namespace spdy
+
+#endif  // QUICHE_SPDY_CORE_SPDY_DEFRAMER_VISITOR_H_
diff --git a/spdy/core/spdy_deframer_visitor_test.cc b/spdy/core/spdy_deframer_visitor_test.cc
new file mode 100644
index 0000000..ede1a20
--- /dev/null
+++ b/spdy/core/spdy_deframer_visitor_test.cc
@@ -0,0 +1,247 @@
+// Copyright 2016 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "net/third_party/quiche/src/spdy/core/spdy_deframer_visitor.h"
+
+#include <stdlib.h>
+
+#include <algorithm>
+#include <limits>
+
+#include "base/logging.h"
+#include "testing/gtest/include/gtest/gtest.h"
+#include "net/third_party/quiche/src/http2/test_tools/http2_random.h"
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_constants.h"
+#include "net/third_party/quiche/src/spdy/core/mock_spdy_framer_visitor.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_frame_builder.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_frame_reader.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_framer.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_protocol.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_protocol_test_utils.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_test_utils.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_ptr_util.h"
+
+namespace spdy {
+namespace test {
+namespace {
+
+class SpdyDeframerVisitorTest : public ::testing::Test {
+ protected:
+  SpdyDeframerVisitorTest() : encoder_(SpdyFramer::ENABLE_COMPRESSION) {
+    decoder_.set_process_single_input_frame(true);
+    auto collector =
+        SpdyMakeUnique<DeframerCallbackCollector>(&collected_frames_);
+    auto log_and_collect =
+        SpdyDeframerVisitorInterface::LogBeforeVisiting(std::move(collector));
+    deframer_ = SpdyTestDeframer::CreateConverter(std::move(log_and_collect));
+    decoder_.set_visitor(deframer_.get());
+  }
+
+  bool DeframeInput(const char* input, size_t size) {
+    size_t input_remaining = size;
+    while (input_remaining > 0 &&
+           decoder_.spdy_framer_error() ==
+               http2::Http2DecoderAdapter::SPDY_NO_ERROR) {
+      // To make the tests more interesting, we feed random (and small) chunks
+      // into the framer.  This simulates getting strange-sized reads from
+      // the socket.
+      const size_t kMaxReadSize = 32;
+      size_t bytes_read =
+          (random_.Uniform(std::min(input_remaining, kMaxReadSize))) + 1;
+      size_t bytes_processed = decoder_.ProcessInput(input, bytes_read);
+      input_remaining -= bytes_processed;
+      input += bytes_processed;
+      if (decoder_.state() ==
+          http2::Http2DecoderAdapter::SPDY_READY_FOR_FRAME) {
+        deframer_->AtFrameEnd();
+      }
+    }
+    return (input_remaining == 0 &&
+            decoder_.spdy_framer_error() ==
+                http2::Http2DecoderAdapter::SPDY_NO_ERROR);
+  }
+
+  SpdyFramer encoder_;
+  http2::Http2DecoderAdapter decoder_;
+  std::vector<CollectedFrame> collected_frames_;
+  std::unique_ptr<SpdyTestDeframer> deframer_;
+
+ private:
+  http2::test::Http2Random random_;
+};
+
+TEST_F(SpdyDeframerVisitorTest, DataFrame) {
+  const char kFrameData[] = {
+      0x00, 0x00, 0x0d,        // Length = 13.
+      0x00,                    // DATA
+      0x08,                    // PADDED
+      0x00, 0x00, 0x00, 0x01,  // Stream 1
+      0x07,                    // Pad length field.
+      'h',  'e',  'l',  'l',   // Data
+      'o',                     // More Data
+      0x00, 0x00, 0x00, 0x00,  // Padding
+      0x00, 0x00, 0x00         // More Padding
+  };
+
+  EXPECT_TRUE(DeframeInput(kFrameData, sizeof kFrameData));
+  ASSERT_EQ(1u, collected_frames_.size());
+  const CollectedFrame& cf0 = collected_frames_[0];
+  ASSERT_NE(cf0.frame_ir, nullptr);
+
+  SpdyDataIR expected_ir(/* stream_id = */ 1, "hello");
+  expected_ir.set_padding_len(8);
+  EXPECT_TRUE(cf0.VerifyHasFrame(expected_ir));
+}
+
+TEST_F(SpdyDeframerVisitorTest, HeaderFrameWithContinuation) {
+  const char kFrameData[] = {
+      0x00, 0x00, 0x05,        // Payload Length: 5
+      0x01,                    // Type: HEADERS
+      0x09,                    // Flags: PADDED | END_STREAM
+      0x00, 0x00, 0x00, 0x01,  // Stream: 1
+      0x04,                    // Padding Length: 4
+      0x00, 0x00, 0x00, 0x00,  // Padding
+      /* Second Frame */
+      0x00, 0x00, 0x12,        // Payload Length: 18
+      0x09,                    // Type: CONTINUATION
+      0x04,                    // Flags: END_HEADERS
+      0x00, 0x00, 0x00, 0x01,  // Stream: 1
+      0x00,                    // Unindexed, literal name & value
+      0x03, 0x62, 0x61, 0x72,  // Name len and name (3, "bar")
+      0x03, 0x66, 0x6f, 0x6f,  // Value len and value (3, "foo")
+      0x00,                    // Unindexed, literal name & value
+      0x03, 0x66, 0x6f, 0x6f,  // Name len and name (3, "foo")
+      0x03, 0x62, 0x61, 0x72,  // Value len and value (3, "bar")
+  };
+
+  EXPECT_TRUE(DeframeInput(kFrameData, sizeof kFrameData));
+  ASSERT_EQ(1u, collected_frames_.size());
+  const CollectedFrame& cf0 = collected_frames_[0];
+
+  StringPairVector headers;
+  headers.push_back({"bar", "foo"});
+  headers.push_back({"foo", "bar"});
+
+  EXPECT_TRUE(cf0.VerifyHasHeaders(headers));
+
+  SpdyHeadersIR expected_ir(/* stream_id = */ 1);
+  // Yet again SpdyFramerVisitorInterface is lossy: it doesn't call OnPadding
+  // for HEADERS, just for DATA. Sigh.
+  //    expected_ir.set_padding_len(5);
+  expected_ir.set_fin(true);
+  for (const auto& nv : headers) {
+    expected_ir.SetHeader(nv.first, nv.second);
+  }
+
+  EXPECT_TRUE(cf0.VerifyHasFrame(expected_ir));
+
+  // Confirm that mismatches are also detected.
+  headers.push_back({"baz", "bing"});
+  EXPECT_FALSE(cf0.VerifyHasHeaders(headers));
+  EXPECT_TRUE(cf0.VerifyHasFrame(expected_ir));
+
+  headers.pop_back();
+  EXPECT_TRUE(cf0.VerifyHasHeaders(headers));
+  EXPECT_TRUE(cf0.VerifyHasFrame(expected_ir));
+
+  expected_ir.SetHeader("baz", "bing");
+  EXPECT_FALSE(cf0.VerifyHasFrame(expected_ir));
+  EXPECT_TRUE(cf0.VerifyHasHeaders(headers));
+}
+
+TEST_F(SpdyDeframerVisitorTest, PriorityFrame) {
+  const char kFrameData[] = {
+      0x00,   0x00, 0x05,        // Length: 5
+      0x02,                      //   Type: PRIORITY
+      0x00,                      //  Flags: none
+      0x00,   0x00, 0x00, 0x65,  // Stream: 101
+      '\x80', 0x00, 0x00, 0x01,  // Parent: 1 (Exclusive)
+      0x10,                      // Weight: 17
+  };
+
+  EXPECT_TRUE(DeframeInput(kFrameData, sizeof kFrameData));
+  ASSERT_EQ(1u, collected_frames_.size());
+  const CollectedFrame& cf0 = collected_frames_[0];
+
+  SpdyPriorityIR expected_ir(/* stream_id = */ 101,
+                             /* parent_stream_id = */ 1, /* weight = */ 17,
+                             /* exclusive = */ true);
+  EXPECT_TRUE(cf0.VerifyHasFrame(expected_ir));
+
+  // Confirm that mismatches are also detected.
+  EXPECT_FALSE(cf0.VerifyHasFrame(SpdyPriorityIR(101, 1, 16, true)));
+  EXPECT_FALSE(cf0.VerifyHasFrame(SpdyPriorityIR(101, 50, 17, true)));
+  EXPECT_FALSE(cf0.VerifyHasFrame(SpdyPriorityIR(201, 1, 17, true)));
+  EXPECT_FALSE(cf0.VerifyHasFrame(SpdyPriorityIR(101, 1, 17, false)));
+}
+
+TEST_F(SpdyDeframerVisitorTest, DISABLED_RstStreamFrame) {
+  // TODO(jamessynge): Please implement.
+}
+
+TEST_F(SpdyDeframerVisitorTest, SettingsFrame) {
+  // Settings frame with two entries for the same parameter but with different
+  // values. The last one will be in the decoded SpdySettingsIR, but the vector
+  // of settings will have both, in the same order.
+  const char kFrameData[] = {
+      0x00, 0x00, 0x0c,          // Length
+      0x04,                      // Type (SETTINGS)
+      0x00,                      // Flags
+      0x00, 0x00, 0x00, 0x00,    // Stream id (must be zero)
+      0x00, 0x04,                // Setting id (SETTINGS_INITIAL_WINDOW_SIZE)
+      0x0a, 0x0b, 0x0c, 0x0d,    // Setting value
+      0x00, 0x04,                // Setting id (SETTINGS_INITIAL_WINDOW_SIZE)
+      0x00, 0x00, 0x00, '\xff',  // Setting value
+  };
+
+  EXPECT_TRUE(DeframeInput(kFrameData, sizeof kFrameData));
+  ASSERT_EQ(1u, collected_frames_.size());
+  const CollectedFrame& cf0 = collected_frames_[0];
+  ASSERT_NE(cf0.frame_ir, nullptr);
+
+  SpdySettingsIR expected_ir;
+  expected_ir.AddSetting(SETTINGS_INITIAL_WINDOW_SIZE, 255);
+  EXPECT_TRUE(cf0.VerifyHasFrame(expected_ir));
+
+  SettingVector expected_settings;
+  expected_settings.push_back({SETTINGS_INITIAL_WINDOW_SIZE, 0x0a0b0c0d});
+  expected_settings.push_back({SETTINGS_INITIAL_WINDOW_SIZE, 255});
+
+  EXPECT_TRUE(cf0.VerifyHasSettings(expected_settings));
+
+  // Confirm that mismatches are also detected.
+  expected_settings.push_back({SETTINGS_INITIAL_WINDOW_SIZE, 65536});
+  EXPECT_FALSE(cf0.VerifyHasSettings(expected_settings));
+
+  expected_ir.AddSetting(SETTINGS_INITIAL_WINDOW_SIZE, 65536);
+  EXPECT_FALSE(cf0.VerifyHasFrame(expected_ir));
+
+  SpdySettingsIR unexpected_ir;
+  unexpected_ir.set_is_ack(true);
+  EXPECT_FALSE(cf0.VerifyHasFrame(unexpected_ir));
+}
+
+TEST_F(SpdyDeframerVisitorTest, DISABLED_PushPromiseFrame) {
+  // TODO(jamessynge): Please implement.
+}
+
+TEST_F(SpdyDeframerVisitorTest, DISABLED_PingFrame) {
+  // TODO(jamessynge): Please implement.
+}
+
+TEST_F(SpdyDeframerVisitorTest, DISABLED_GoAwayFrame) {
+  // TODO(jamessynge): Please implement.
+}
+
+TEST_F(SpdyDeframerVisitorTest, DISABLED_WindowUpdateFrame) {
+  // TODO(jamessynge): Please implement.
+}
+
+TEST_F(SpdyDeframerVisitorTest, DISABLED_AltSvcFrame) {
+  // TODO(jamessynge): Please implement.
+}
+
+}  // namespace
+}  // namespace test
+}  // namespace spdy
diff --git a/spdy/core/spdy_frame_builder.cc b/spdy/core/spdy_frame_builder.cc
new file mode 100644
index 0000000..a056b70
--- /dev/null
+++ b/spdy/core/spdy_frame_builder.cc
@@ -0,0 +1,183 @@
+// Copyright (c) 2012 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "net/third_party/quiche/src/spdy/core/spdy_frame_builder.h"
+
+#include <algorithm>
+#include <cstdint>
+#include <limits>
+#include <new>
+
+#include "base/logging.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_protocol.h"
+#include "net/third_party/quiche/src/spdy/core/zero_copy_output_buffer.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_bug_tracker.h"
+
+namespace spdy {
+
+SpdyFrameBuilder::SpdyFrameBuilder(size_t size)
+    : buffer_(new char[size]), capacity_(size), length_(0), offset_(0) {}
+
+SpdyFrameBuilder::SpdyFrameBuilder(size_t size, ZeroCopyOutputBuffer* output)
+    : buffer_(output == nullptr ? new char[size] : nullptr),
+      output_(output),
+      capacity_(size),
+      length_(0),
+      offset_(0) {}
+
+SpdyFrameBuilder::~SpdyFrameBuilder() = default;
+
+char* SpdyFrameBuilder::GetWritableBuffer(size_t length) {
+  if (!CanWrite(length)) {
+    return nullptr;
+  }
+  return buffer_.get() + offset_ + length_;
+}
+
+char* SpdyFrameBuilder::GetWritableOutput(size_t length,
+                                          size_t* actual_length) {
+  char* dest = nullptr;
+  int size = 0;
+
+  if (!CanWrite(length)) {
+    return nullptr;
+  }
+  output_->Next(&dest, &size);
+  *actual_length = std::min<size_t>(length, size);
+  return dest;
+}
+
+bool SpdyFrameBuilder::Seek(size_t length) {
+  if (!CanWrite(length)) {
+    return false;
+  }
+  if (output_ == nullptr) {
+    length_ += length;
+  } else {
+    output_->AdvanceWritePtr(length);
+    length_ += length;
+  }
+  return true;
+}
+
+bool SpdyFrameBuilder::BeginNewFrame(SpdyFrameType type,
+                                     uint8_t flags,
+                                     SpdyStreamId stream_id) {
+  uint8_t raw_frame_type = SerializeFrameType(type);
+  DCHECK(IsDefinedFrameType(raw_frame_type));
+  DCHECK_EQ(0u, stream_id & ~kStreamIdMask);
+  bool success = true;
+  if (length_ > 0) {
+    SPDY_BUG << "SpdyFrameBuilder doesn't have a clean state when BeginNewFrame"
+             << "is called. Leftover length_ is " << length_;
+    offset_ += length_;
+    length_ = 0;
+  }
+
+  success &= WriteUInt24(capacity_ - offset_ - kFrameHeaderSize);
+  success &= WriteUInt8(raw_frame_type);
+  success &= WriteUInt8(flags);
+  success &= WriteUInt32(stream_id);
+  DCHECK_EQ(kDataFrameMinimumSize, length_);
+  return success;
+}
+
+bool SpdyFrameBuilder::BeginNewFrame(SpdyFrameType type,
+                                     uint8_t flags,
+                                     SpdyStreamId stream_id,
+                                     size_t length) {
+  uint8_t raw_frame_type = SerializeFrameType(type);
+  DCHECK(IsDefinedFrameType(raw_frame_type));
+  DCHECK_EQ(0u, stream_id & ~kStreamIdMask);
+  SPDY_BUG_IF(length > kHttp2DefaultFramePayloadLimit)
+      << "Frame length  " << length_ << " is longer than frame size limit.";
+  return BeginNewFrameInternal(raw_frame_type, flags, stream_id, length);
+}
+
+bool SpdyFrameBuilder::BeginNewUncheckedFrame(uint8_t raw_frame_type,
+                                              uint8_t flags,
+                                              SpdyStreamId stream_id,
+                                              size_t length) {
+  return BeginNewFrameInternal(raw_frame_type, flags, stream_id, length);
+}
+
+bool SpdyFrameBuilder::BeginNewFrameInternal(uint8_t raw_frame_type,
+                                             uint8_t flags,
+                                             SpdyStreamId stream_id,
+                                             size_t length) {
+  DCHECK_EQ(length, length & kLengthMask);
+  bool success = true;
+
+  offset_ += length_;
+  length_ = 0;
+
+  success &= WriteUInt24(length);
+  success &= WriteUInt8(raw_frame_type);
+  success &= WriteUInt8(flags);
+  success &= WriteUInt32(stream_id);
+  DCHECK_EQ(kDataFrameMinimumSize, length_);
+  return success;
+}
+
+bool SpdyFrameBuilder::WriteStringPiece32(const SpdyStringPiece value) {
+  if (!WriteUInt32(value.size())) {
+    return false;
+  }
+
+  return WriteBytes(value.data(), value.size());
+}
+
+bool SpdyFrameBuilder::WriteBytes(const void* data, uint32_t data_len) {
+  if (!CanWrite(data_len)) {
+    return false;
+  }
+
+  if (output_ == nullptr) {
+    char* dest = GetWritableBuffer(data_len);
+    memcpy(dest, data, data_len);
+    Seek(data_len);
+  } else {
+    char* dest = nullptr;
+    size_t size = 0;
+    size_t total_written = 0;
+    const char* data_ptr = reinterpret_cast<const char*>(data);
+    while (data_len > 0) {
+      dest = GetWritableOutput(data_len, &size);
+      if (dest == nullptr || size == 0) {
+        // Unable to make progress.
+        return false;
+      }
+      uint32_t to_copy = std::min<uint32_t>(data_len, size);
+      const char* src = data_ptr + total_written;
+      memcpy(dest, src, to_copy);
+      Seek(to_copy);
+      data_len -= to_copy;
+      total_written += to_copy;
+    }
+  }
+  return true;
+}
+
+bool SpdyFrameBuilder::CanWrite(size_t length) const {
+  if (length > kLengthMask) {
+    DCHECK(false);
+    return false;
+  }
+
+  if (output_ == nullptr) {
+    if (offset_ + length_ + length > capacity_) {
+      DLOG(FATAL) << "Requested: " << length << " capacity: " << capacity_
+                  << " used: " << offset_ + length_;
+      return false;
+    }
+  } else {
+    if (length > output_->BytesFree()) {
+      return false;
+    }
+  }
+
+  return true;
+}
+
+}  // namespace spdy
diff --git a/spdy/core/spdy_frame_builder.h b/spdy/core/spdy_frame_builder.h
new file mode 100644
index 0000000..c569c8c
--- /dev/null
+++ b/spdy/core/spdy_frame_builder.h
@@ -0,0 +1,142 @@
+// Copyright (c) 2012 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef QUICHE_SPDY_CORE_SPDY_FRAME_BUILDER_H_
+#define QUICHE_SPDY_CORE_SPDY_FRAME_BUILDER_H_
+
+#include <cstddef>
+#include <cstdint>
+#include <memory>
+
+#include "net/third_party/quiche/src/spdy/core/spdy_protocol.h"
+#include "net/third_party/quiche/src/spdy/core/zero_copy_output_buffer.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_bug_tracker.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_endianness_util.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_export.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string_piece.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_test_utils_prod.h"
+
+namespace spdy {
+
+// This class provides facilities for basic binary value packing
+// into Spdy frames.
+//
+// The SpdyFrameBuilder supports appending primitive values (int, string, etc)
+// to a frame instance.  The SpdyFrameBuilder grows its internal memory buffer
+// dynamically to hold the sequence of primitive values.   The internal memory
+// buffer is exposed as the "data" of the SpdyFrameBuilder.
+class SPDY_EXPORT_PRIVATE SpdyFrameBuilder {
+ public:
+  // Initializes a SpdyFrameBuilder with a buffer of given size
+  explicit SpdyFrameBuilder(size_t size);
+  // Doesn't take ownership of output.
+  SpdyFrameBuilder(size_t size, ZeroCopyOutputBuffer* output);
+
+  ~SpdyFrameBuilder();
+
+  // Returns the total size of the SpdyFrameBuilder's data, which may include
+  // multiple frames.
+  size_t length() const { return offset_ + length_; }
+
+  // Seeks forward by the given number of bytes. Useful in conjunction with
+  // GetWriteableBuffer() above.
+  bool Seek(size_t length);
+
+  // Populates this frame with a HTTP2 frame prefix using length information
+  // from |capacity_|. The given type must be a control frame type.
+  bool BeginNewFrame(SpdyFrameType type, uint8_t flags, SpdyStreamId stream_id);
+
+  // Populates this frame with a HTTP2 frame prefix with type and length
+  // information.  |type| must be a defined frame type.
+  bool BeginNewFrame(SpdyFrameType type,
+                     uint8_t flags,
+                     SpdyStreamId stream_id,
+                     size_t length);
+
+  // Populates this frame with a HTTP2 frame prefix with type and length
+  // information.  |raw_frame_type| may be a defined or undefined frame type.
+  bool BeginNewUncheckedFrame(uint8_t raw_frame_type,
+                              uint8_t flags,
+                              SpdyStreamId stream_id,
+                              size_t length);
+
+  // Takes the buffer from the SpdyFrameBuilder.
+  SpdySerializedFrame take() {
+    SPDY_BUG_IF(output_ != nullptr) << "ZeroCopyOutputBuffer is used to build "
+                                    << "frames. take() shouldn't be called";
+    SPDY_BUG_IF(kMaxFrameSizeLimit < length_)
+        << "Frame length " << length_
+        << " is longer than the maximum possible allowed length.";
+    SpdySerializedFrame rv(buffer_.release(), length(), true);
+    capacity_ = 0;
+    length_ = 0;
+    offset_ = 0;
+    return rv;
+  }
+
+  // Methods for adding to the payload.  These values are appended to the end
+  // of the SpdyFrameBuilder payload. Note - binary integers are converted from
+  // host to network form.
+  bool WriteUInt8(uint8_t value) { return WriteBytes(&value, sizeof(value)); }
+  bool WriteUInt16(uint16_t value) {
+    value = SpdyHostToNet16(value);
+    return WriteBytes(&value, sizeof(value));
+  }
+  bool WriteUInt24(uint32_t value) {
+    value = SpdyHostToNet32(value);
+    return WriteBytes(reinterpret_cast<char*>(&value) + 1, sizeof(value) - 1);
+  }
+  bool WriteUInt32(uint32_t value) {
+    value = SpdyHostToNet32(value);
+    return WriteBytes(&value, sizeof(value));
+  }
+  bool WriteUInt64(uint64_t value) {
+    uint32_t upper = SpdyHostToNet32(static_cast<uint32_t>(value >> 32));
+    uint32_t lower = SpdyHostToNet32(static_cast<uint32_t>(value));
+    return (WriteBytes(&upper, sizeof(upper)) &&
+            WriteBytes(&lower, sizeof(lower)));
+  }
+  bool WriteStringPiece32(const SpdyStringPiece value);
+  bool WriteBytes(const void* data, uint32_t data_len);
+
+ private:
+  SPDY_FRIEND_TEST(SpdyFrameBuilderTest, GetWritableBuffer);
+  SPDY_FRIEND_TEST(SpdyFrameBuilderTest, GetWritableOutput);
+  SPDY_FRIEND_TEST(SpdyFrameBuilderTest, GetWritableOutputNegative);
+
+  // Populates this frame with a HTTP2 frame prefix with type and length
+  // information.
+  bool BeginNewFrameInternal(uint8_t raw_frame_type,
+                             uint8_t flags,
+                             SpdyStreamId stream_id,
+                             size_t length);
+
+  // Returns a writeable buffer of given size in bytes, to be appended to the
+  // currently written frame. Does bounds checking on length but does not
+  // increment the underlying iterator. To do so, consumers should subsequently
+  // call Seek().
+  // In general, consumers should use Write*() calls instead of this.
+  // Returns NULL on failure.
+  char* GetWritableBuffer(size_t length);
+  char* GetWritableOutput(size_t desired_length, size_t* actual_length);
+
+  // Checks to make sure that there is an appropriate amount of space for a
+  // write of given size, in bytes.
+  bool CanWrite(size_t length) const;
+
+  // A buffer to be created whenever a new frame needs to be written. Used only
+  // if |output_| is nullptr.
+  std::unique_ptr<char[]> buffer_;
+  // A pre-allocated buffer. If not-null, serialized frame data is written to
+  // this buffer.
+  ZeroCopyOutputBuffer* output_ = nullptr;  // Does not own.
+
+  size_t capacity_;  // Allocation size of payload, set by constructor.
+  size_t length_;    // Length of the latest frame in the buffer.
+  size_t offset_;    // Position at which the latest frame begins.
+};
+
+}  // namespace spdy
+
+#endif  // QUICHE_SPDY_CORE_SPDY_FRAME_BUILDER_H_
diff --git a/spdy/core/spdy_frame_builder_test.cc b/spdy/core/spdy_frame_builder_test.cc
new file mode 100644
index 0000000..97d10f1
--- /dev/null
+++ b/spdy/core/spdy_frame_builder_test.cc
@@ -0,0 +1,68 @@
+// Copyright (c) 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "net/third_party/quiche/src/spdy/core/spdy_frame_builder.h"
+
+#include <memory>
+
+#include "testing/gtest/include/gtest/gtest.h"
+#include "net/third_party/quiche/src/spdy/core/array_output_buffer.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_framer.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_protocol.h"
+
+namespace spdy {
+
+namespace {
+
+const int64_t kSize = 64 * 1024;
+char output_buffer[kSize] = "";
+
+}  // namespace
+
+// Verifies that SpdyFrameBuilder::GetWritableBuffer() can be used to build a
+// SpdySerializedFrame.
+TEST(SpdyFrameBuilderTest, GetWritableBuffer) {
+  const size_t kBuilderSize = 10;
+  SpdyFrameBuilder builder(kBuilderSize);
+  char* writable_buffer = builder.GetWritableBuffer(kBuilderSize);
+  memset(writable_buffer, ~1, kBuilderSize);
+  EXPECT_TRUE(builder.Seek(kBuilderSize));
+  SpdySerializedFrame frame(builder.take());
+  char expected[kBuilderSize];
+  memset(expected, ~1, kBuilderSize);
+  EXPECT_EQ(SpdyStringPiece(expected, kBuilderSize),
+            SpdyStringPiece(frame.data(), kBuilderSize));
+}
+
+// Verifies that SpdyFrameBuilder::GetWritableBuffer() can be used to build a
+// SpdySerializedFrame to the output buffer.
+TEST(SpdyFrameBuilderTest, GetWritableOutput) {
+  ArrayOutputBuffer output(output_buffer, kSize);
+  const size_t kBuilderSize = 10;
+  SpdyFrameBuilder builder(kBuilderSize, &output);
+  size_t actual_size = 0;
+  char* writable_buffer = builder.GetWritableOutput(kBuilderSize, &actual_size);
+  memset(writable_buffer, ~1, kBuilderSize);
+  EXPECT_TRUE(builder.Seek(kBuilderSize));
+  SpdySerializedFrame frame(output.Begin(), kBuilderSize, false);
+  char expected[kBuilderSize];
+  memset(expected, ~1, kBuilderSize);
+  EXPECT_EQ(SpdyStringPiece(expected, kBuilderSize),
+            SpdyStringPiece(frame.data(), kBuilderSize));
+}
+
+// Verifies the case that the buffer's capacity is too small.
+TEST(SpdyFrameBuilderTest, GetWritableOutputNegative) {
+  size_t small_cap = 1;
+  ArrayOutputBuffer output(output_buffer, small_cap);
+  const size_t kBuilderSize = 10;
+  SpdyFrameBuilder builder(kBuilderSize, &output);
+  size_t actual_size = 0;
+  char* writable_buffer = builder.GetWritableOutput(kBuilderSize, &actual_size);
+  builder.GetWritableOutput(kBuilderSize, &actual_size);
+  EXPECT_EQ(0u, actual_size);
+  EXPECT_EQ(nullptr, writable_buffer);
+}
+
+}  // namespace spdy
diff --git a/spdy/core/spdy_frame_reader.cc b/spdy/core/spdy_frame_reader.cc
new file mode 100644
index 0000000..b9bf4c1
--- /dev/null
+++ b/spdy/core/spdy_frame_reader.cc
@@ -0,0 +1,200 @@
+// Copyright (c) 2012 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "net/third_party/quiche/src/spdy/core/spdy_frame_reader.h"
+
+#include "net/third_party/quiche/src/spdy/core/spdy_protocol.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_endianness_util.h"
+
+namespace spdy {
+
+SpdyFrameReader::SpdyFrameReader(const char* data, const size_t len)
+    : data_(data), len_(len), ofs_(0) {}
+
+bool SpdyFrameReader::ReadUInt8(uint8_t* result) {
+  // Make sure that we have the whole uint8_t.
+  if (!CanRead(1)) {
+    OnFailure();
+    return false;
+  }
+
+  // Read into result.
+  *result = *reinterpret_cast<const uint8_t*>(data_ + ofs_);
+
+  // Iterate.
+  ofs_ += 1;
+
+  return true;
+}
+
+bool SpdyFrameReader::ReadUInt16(uint16_t* result) {
+  // Make sure that we have the whole uint16_t.
+  if (!CanRead(2)) {
+    OnFailure();
+    return false;
+  }
+
+  // Read into result.
+  *result = SpdyNetToHost16(*(reinterpret_cast<const uint16_t*>(data_ + ofs_)));
+
+  // Iterate.
+  ofs_ += 2;
+
+  return true;
+}
+
+bool SpdyFrameReader::ReadUInt32(uint32_t* result) {
+  // Make sure that we have the whole uint32_t.
+  if (!CanRead(4)) {
+    OnFailure();
+    return false;
+  }
+
+  // Read into result.
+  *result = SpdyNetToHost32(*(reinterpret_cast<const uint32_t*>(data_ + ofs_)));
+
+  // Iterate.
+  ofs_ += 4;
+
+  return true;
+}
+
+bool SpdyFrameReader::ReadUInt64(uint64_t* result) {
+  // Make sure that we have the whole uint64_t.
+  if (!CanRead(8)) {
+    OnFailure();
+    return false;
+  }
+
+  // Read into result. Network byte order is big-endian.
+  uint64_t upper =
+      SpdyNetToHost32(*(reinterpret_cast<const uint32_t*>(data_ + ofs_)));
+  uint64_t lower =
+      SpdyNetToHost32(*(reinterpret_cast<const uint32_t*>(data_ + ofs_ + 4)));
+  *result = (upper << 32) + lower;
+
+  // Iterate.
+  ofs_ += 8;
+
+  return true;
+}
+
+bool SpdyFrameReader::ReadUInt31(uint32_t* result) {
+  bool success = ReadUInt32(result);
+
+  // Zero out highest-order bit.
+  if (success) {
+    *result &= 0x7fffffff;
+  }
+
+  return success;
+}
+
+bool SpdyFrameReader::ReadUInt24(uint32_t* result) {
+  // Make sure that we have the whole uint24_t.
+  if (!CanRead(3)) {
+    OnFailure();
+    return false;
+  }
+
+  // Read into result.
+  *result = 0;
+  memcpy(reinterpret_cast<char*>(result) + 1, data_ + ofs_, 3);
+  *result = SpdyNetToHost32(*result);
+
+  // Iterate.
+  ofs_ += 3;
+
+  return true;
+}
+
+bool SpdyFrameReader::ReadStringPiece16(SpdyStringPiece* result) {
+  // Read resultant length.
+  uint16_t result_len;
+  if (!ReadUInt16(&result_len)) {
+    // OnFailure() already called.
+    return false;
+  }
+
+  // Make sure that we have the whole string.
+  if (!CanRead(result_len)) {
+    OnFailure();
+    return false;
+  }
+
+  // Set result.
+  *result = SpdyStringPiece(data_ + ofs_, result_len);
+
+  // Iterate.
+  ofs_ += result_len;
+
+  return true;
+}
+
+bool SpdyFrameReader::ReadStringPiece32(SpdyStringPiece* result) {
+  // Read resultant length.
+  uint32_t result_len;
+  if (!ReadUInt32(&result_len)) {
+    // OnFailure() already called.
+    return false;
+  }
+
+  // Make sure that we have the whole string.
+  if (!CanRead(result_len)) {
+    OnFailure();
+    return false;
+  }
+
+  // Set result.
+  *result = SpdyStringPiece(data_ + ofs_, result_len);
+
+  // Iterate.
+  ofs_ += result_len;
+
+  return true;
+}
+
+bool SpdyFrameReader::ReadBytes(void* result, size_t size) {
+  // Make sure that we have enough data to read.
+  if (!CanRead(size)) {
+    OnFailure();
+    return false;
+  }
+
+  // Read into result.
+  memcpy(result, data_ + ofs_, size);
+
+  // Iterate.
+  ofs_ += size;
+
+  return true;
+}
+
+bool SpdyFrameReader::Seek(size_t size) {
+  if (!CanRead(size)) {
+    OnFailure();
+    return false;
+  }
+
+  // Iterate.
+  ofs_ += size;
+
+  return true;
+}
+
+bool SpdyFrameReader::IsDoneReading() const {
+  return len_ == ofs_;
+}
+
+bool SpdyFrameReader::CanRead(size_t bytes) const {
+  return bytes <= (len_ - ofs_);
+}
+
+void SpdyFrameReader::OnFailure() {
+  // Set our iterator to the end of the buffer so that further reads fail
+  // immediately.
+  ofs_ = len_;
+}
+
+}  // namespace spdy
diff --git a/spdy/core/spdy_frame_reader.h b/spdy/core/spdy_frame_reader.h
new file mode 100644
index 0000000..dc6c064
--- /dev/null
+++ b/spdy/core/spdy_frame_reader.h
@@ -0,0 +1,129 @@
+// Copyright (c) 2012 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef QUICHE_SPDY_CORE_SPDY_FRAME_READER_H_
+#define QUICHE_SPDY_CORE_SPDY_FRAME_READER_H_
+
+#include <cstdint>
+
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_export.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string_piece.h"
+
+namespace spdy {
+
+// Used for reading SPDY frames. Though there isn't really anything terribly
+// SPDY-specific here, it's a helper class that's useful when doing SPDY
+// framing.
+//
+// To use, simply construct a SpdyFramerReader using the underlying buffer that
+// you'd like to read fields from, then call one of the Read*() methods to
+// actually do some reading.
+//
+// This class keeps an internal iterator to keep track of what's already been
+// read and each successive Read*() call automatically increments said iterator
+// on success. On failure, internal state of the SpdyFrameReader should not be
+// trusted and it is up to the caller to throw away the failed instance and
+// handle the error as appropriate. None of the Read*() methods should ever be
+// called after failure, as they will also fail immediately.
+class SPDY_EXPORT_PRIVATE SpdyFrameReader {
+ public:
+  // Caller must provide an underlying buffer to work on.
+  SpdyFrameReader(const char* data, const size_t len);
+
+  // Empty destructor.
+  ~SpdyFrameReader() {}
+
+  // Reads an 8-bit unsigned integer into the given output parameter.
+  // Forwards the internal iterator on success.
+  // Returns true on success, false otherwise.
+  bool ReadUInt8(uint8_t* result);
+
+  // Reads a 16-bit unsigned integer into the given output parameter.
+  // Forwards the internal iterator on success.
+  // Returns true on success, false otherwise.
+  bool ReadUInt16(uint16_t* result);
+
+  // Reads a 32-bit unsigned integer into the given output parameter.
+  // Forwards the internal iterator on success.
+  // Returns true on success, false otherwise.
+  bool ReadUInt32(uint32_t* result);
+
+  // Reads a 64-bit unsigned integer into the given output parameter.
+  // Forwards the internal iterator on success.
+  // Returns true on success, false otherwise.
+  bool ReadUInt64(uint64_t* result);
+
+  // Reads a 31-bit unsigned integer into the given output parameter. This is
+  // equivalent to ReadUInt32() above except that the highest-order bit is
+  // discarded.
+  // Forwards the internal iterator (by 4B) on success.
+  // Returns true on success, false otherwise.
+  bool ReadUInt31(uint32_t* result);
+
+  // Reads a 24-bit unsigned integer into the given output parameter.
+  // Forwards the internal iterator (by 3B) on success.
+  // Returns true on success, false otherwise.
+  bool ReadUInt24(uint32_t* result);
+
+  // Reads a string prefixed with 16-bit length into the given output parameter.
+  //
+  // NOTE: Does not copy but rather references strings in the underlying buffer.
+  // This should be kept in mind when handling memory management!
+  //
+  // Forwards the internal iterator on success.
+  // Returns true on success, false otherwise.
+  bool ReadStringPiece16(SpdyStringPiece* result);
+
+  // Reads a string prefixed with 32-bit length into the given output parameter.
+  //
+  // NOTE: Does not copy but rather references strings in the underlying buffer.
+  // This should be kept in mind when handling memory management!
+  //
+  // Forwards the internal iterator on success.
+  // Returns true on success, false otherwise.
+  bool ReadStringPiece32(SpdyStringPiece* result);
+
+  // Reads a given number of bytes into the given buffer. The buffer
+  // must be of adequate size.
+  // Forwards the internal iterator on success.
+  // Returns true on success, false otherwise.
+  bool ReadBytes(void* result, size_t size);
+
+  // Seeks a given number of bytes into the buffer from the current offset.
+  // Equivelant to an empty read.
+  // Forwards the internal iterator.
+  // Returns true on success, false otherwise.
+  bool Seek(size_t size);
+
+  // Rewinds this reader to the beginning of the frame.
+  void Rewind() { ofs_ = 0; }
+
+  // Returns true if the entirety of the underlying buffer has been read via
+  // Read*() calls.
+  bool IsDoneReading() const;
+
+  // Returns the number of bytes that have been consumed by the reader so far.
+  size_t GetBytesConsumed() const { return ofs_; }
+
+ private:
+  // Returns true if the underlying buffer has enough room to read the given
+  // amount of bytes.
+  bool CanRead(size_t bytes) const;
+
+  // To be called when a read fails for any reason.
+  void OnFailure();
+
+  // The data buffer that we're reading from.
+  const char* data_;
+
+  // The length of the data buffer that we're reading from.
+  const size_t len_;
+
+  // The location of the next read from our data buffer.
+  size_t ofs_;
+};
+
+}  // namespace spdy
+
+#endif  // QUICHE_SPDY_CORE_SPDY_FRAME_READER_H_
diff --git a/spdy/core/spdy_frame_reader_test.cc b/spdy/core/spdy_frame_reader_test.cc
new file mode 100644
index 0000000..8caf60f
--- /dev/null
+++ b/spdy/core/spdy_frame_reader_test.cc
@@ -0,0 +1,247 @@
+// Copyright (c) 2012 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "net/third_party/quiche/src/spdy/core/spdy_frame_reader.h"
+
+#include <cstdint>
+
+#include "testing/gtest/include/gtest/gtest.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_arraysize.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_endianness_util.h"
+
+namespace spdy {
+
+TEST(SpdyFrameReaderTest, ReadUInt16) {
+  // Frame data in network byte order.
+  const uint16_t kFrameData[] = {
+      SpdyHostToNet16(1),
+      SpdyHostToNet16(1 << 15),
+  };
+
+  SpdyFrameReader frame_reader(reinterpret_cast<const char*>(kFrameData),
+                               sizeof(kFrameData));
+  EXPECT_FALSE(frame_reader.IsDoneReading());
+
+  uint16_t uint16_val;
+  EXPECT_TRUE(frame_reader.ReadUInt16(&uint16_val));
+  EXPECT_FALSE(frame_reader.IsDoneReading());
+  EXPECT_EQ(1, uint16_val);
+
+  EXPECT_TRUE(frame_reader.ReadUInt16(&uint16_val));
+  EXPECT_TRUE(frame_reader.IsDoneReading());
+  EXPECT_EQ(1 << 15, uint16_val);
+}
+
+TEST(SpdyFrameReaderTest, ReadUInt32) {
+  // Frame data in network byte order.
+  const uint32_t kFrameData[] = {
+      SpdyHostToNet32(1),
+      SpdyHostToNet32(0x80000000),
+  };
+
+  SpdyFrameReader frame_reader(reinterpret_cast<const char*>(kFrameData),
+                               SPDY_ARRAYSIZE(kFrameData) * sizeof(uint32_t));
+  EXPECT_FALSE(frame_reader.IsDoneReading());
+
+  uint32_t uint32_val;
+  EXPECT_TRUE(frame_reader.ReadUInt32(&uint32_val));
+  EXPECT_FALSE(frame_reader.IsDoneReading());
+  EXPECT_EQ(1u, uint32_val);
+
+  EXPECT_TRUE(frame_reader.ReadUInt32(&uint32_val));
+  EXPECT_TRUE(frame_reader.IsDoneReading());
+  EXPECT_EQ(1u << 31, uint32_val);
+}
+
+TEST(SpdyFrameReaderTest, ReadStringPiece16) {
+  // Frame data in network byte order.
+  const char kFrameData[] = {
+      0x00, 0x02,  // uint16_t(2)
+      0x48, 0x69,  // "Hi"
+      0x00, 0x10,  // uint16_t(16)
+      0x54, 0x65, 0x73, 0x74, 0x69, 0x6e, 0x67, 0x2c,
+      0x20, 0x31, 0x2c, 0x20, 0x32, 0x2c, 0x20, 0x33,  // "Testing, 1, 2, 3"
+  };
+
+  SpdyFrameReader frame_reader(kFrameData, SPDY_ARRAYSIZE(kFrameData));
+  EXPECT_FALSE(frame_reader.IsDoneReading());
+
+  SpdyStringPiece stringpiece_val;
+  EXPECT_TRUE(frame_reader.ReadStringPiece16(&stringpiece_val));
+  EXPECT_FALSE(frame_reader.IsDoneReading());
+  EXPECT_EQ(0, stringpiece_val.compare("Hi"));
+
+  EXPECT_TRUE(frame_reader.ReadStringPiece16(&stringpiece_val));
+  EXPECT_TRUE(frame_reader.IsDoneReading());
+  EXPECT_EQ(0, stringpiece_val.compare("Testing, 1, 2, 3"));
+}
+
+TEST(SpdyFrameReaderTest, ReadStringPiece32) {
+  // Frame data in network byte order.
+  const char kFrameData[] = {
+      0x00, 0x00, 0x00, 0x03,  // uint32_t(3)
+      0x66, 0x6f, 0x6f,        // "foo"
+      0x00, 0x00, 0x00, 0x10,  // uint32_t(16)
+      0x54, 0x65, 0x73, 0x74, 0x69, 0x6e, 0x67, 0x2c,
+      0x20, 0x34, 0x2c, 0x20, 0x35, 0x2c, 0x20, 0x36,  // "Testing, 4, 5, 6"
+  };
+
+  SpdyFrameReader frame_reader(kFrameData, SPDY_ARRAYSIZE(kFrameData));
+  EXPECT_FALSE(frame_reader.IsDoneReading());
+
+  SpdyStringPiece stringpiece_val;
+  EXPECT_TRUE(frame_reader.ReadStringPiece32(&stringpiece_val));
+  EXPECT_FALSE(frame_reader.IsDoneReading());
+  EXPECT_EQ(0, stringpiece_val.compare("foo"));
+
+  EXPECT_TRUE(frame_reader.ReadStringPiece32(&stringpiece_val));
+  EXPECT_TRUE(frame_reader.IsDoneReading());
+  EXPECT_EQ(0, stringpiece_val.compare("Testing, 4, 5, 6"));
+}
+
+TEST(SpdyFrameReaderTest, ReadUInt16WithBufferTooSmall) {
+  // Frame data in network byte order.
+  const char kFrameData[] = {
+      0x00,  // part of a uint16_t
+  };
+
+  SpdyFrameReader frame_reader(kFrameData, SPDY_ARRAYSIZE(kFrameData));
+  EXPECT_FALSE(frame_reader.IsDoneReading());
+
+  uint16_t uint16_val;
+  EXPECT_FALSE(frame_reader.ReadUInt16(&uint16_val));
+}
+
+TEST(SpdyFrameReaderTest, ReadUInt32WithBufferTooSmall) {
+  // Frame data in network byte order.
+  const char kFrameData[] = {
+      0x00, 0x00, 0x00,  // part of a uint32_t
+  };
+
+  SpdyFrameReader frame_reader(kFrameData, SPDY_ARRAYSIZE(kFrameData));
+  EXPECT_FALSE(frame_reader.IsDoneReading());
+
+  uint32_t uint32_val;
+  EXPECT_FALSE(frame_reader.ReadUInt32(&uint32_val));
+
+  // Also make sure that trying to read a uint16_t, which technically could
+  // work, fails immediately due to previously encountered failed read.
+  uint16_t uint16_val;
+  EXPECT_FALSE(frame_reader.ReadUInt16(&uint16_val));
+}
+
+// Tests ReadStringPiece16() with a buffer too small to fit the entire string.
+TEST(SpdyFrameReaderTest, ReadStringPiece16WithBufferTooSmall) {
+  // Frame data in network byte order.
+  const char kFrameData[] = {
+      0x00, 0x03,  // uint16_t(3)
+      0x48, 0x69,  // "Hi"
+  };
+
+  SpdyFrameReader frame_reader(kFrameData, SPDY_ARRAYSIZE(kFrameData));
+  EXPECT_FALSE(frame_reader.IsDoneReading());
+
+  SpdyStringPiece stringpiece_val;
+  EXPECT_FALSE(frame_reader.ReadStringPiece16(&stringpiece_val));
+
+  // Also make sure that trying to read a uint16_t, which technically could
+  // work, fails immediately due to previously encountered failed read.
+  uint16_t uint16_val;
+  EXPECT_FALSE(frame_reader.ReadUInt16(&uint16_val));
+}
+
+// Tests ReadStringPiece16() with a buffer too small even to fit the length.
+TEST(SpdyFrameReaderTest, ReadStringPiece16WithBufferWayTooSmall) {
+  // Frame data in network byte order.
+  const char kFrameData[] = {
+      0x00,  // part of a uint16_t
+  };
+
+  SpdyFrameReader frame_reader(kFrameData, SPDY_ARRAYSIZE(kFrameData));
+  EXPECT_FALSE(frame_reader.IsDoneReading());
+
+  SpdyStringPiece stringpiece_val;
+  EXPECT_FALSE(frame_reader.ReadStringPiece16(&stringpiece_val));
+
+  // Also make sure that trying to read a uint16_t, which technically could
+  // work, fails immediately due to previously encountered failed read.
+  uint16_t uint16_val;
+  EXPECT_FALSE(frame_reader.ReadUInt16(&uint16_val));
+}
+
+// Tests ReadStringPiece32() with a buffer too small to fit the entire string.
+TEST(SpdyFrameReaderTest, ReadStringPiece32WithBufferTooSmall) {
+  // Frame data in network byte order.
+  const char kFrameData[] = {
+      0x00, 0x00, 0x00, 0x03,  // uint32_t(3)
+      0x48, 0x69,              // "Hi"
+  };
+
+  SpdyFrameReader frame_reader(kFrameData, SPDY_ARRAYSIZE(kFrameData));
+  EXPECT_FALSE(frame_reader.IsDoneReading());
+
+  SpdyStringPiece stringpiece_val;
+  EXPECT_FALSE(frame_reader.ReadStringPiece32(&stringpiece_val));
+
+  // Also make sure that trying to read a uint16_t, which technically could
+  // work, fails immediately due to previously encountered failed read.
+  uint16_t uint16_val;
+  EXPECT_FALSE(frame_reader.ReadUInt16(&uint16_val));
+}
+
+// Tests ReadStringPiece32() with a buffer too small even to fit the length.
+TEST(SpdyFrameReaderTest, ReadStringPiece32WithBufferWayTooSmall) {
+  // Frame data in network byte order.
+  const char kFrameData[] = {
+      0x00, 0x00, 0x00,  // part of a uint32_t
+  };
+
+  SpdyFrameReader frame_reader(kFrameData, SPDY_ARRAYSIZE(kFrameData));
+  EXPECT_FALSE(frame_reader.IsDoneReading());
+
+  SpdyStringPiece stringpiece_val;
+  EXPECT_FALSE(frame_reader.ReadStringPiece32(&stringpiece_val));
+
+  // Also make sure that trying to read a uint16_t, which technically could
+  // work, fails immediately due to previously encountered failed read.
+  uint16_t uint16_val;
+  EXPECT_FALSE(frame_reader.ReadUInt16(&uint16_val));
+}
+
+TEST(SpdyFrameReaderTest, ReadBytes) {
+  // Frame data in network byte order.
+  const char kFrameData[] = {
+      0x66, 0x6f, 0x6f,  // "foo"
+      0x48, 0x69,        // "Hi"
+  };
+
+  SpdyFrameReader frame_reader(kFrameData, SPDY_ARRAYSIZE(kFrameData));
+  EXPECT_FALSE(frame_reader.IsDoneReading());
+
+  char dest1[3] = {};
+  EXPECT_TRUE(frame_reader.ReadBytes(&dest1, SPDY_ARRAYSIZE(dest1)));
+  EXPECT_FALSE(frame_reader.IsDoneReading());
+  EXPECT_EQ("foo", SpdyStringPiece(dest1, SPDY_ARRAYSIZE(dest1)));
+
+  char dest2[2] = {};
+  EXPECT_TRUE(frame_reader.ReadBytes(&dest2, SPDY_ARRAYSIZE(dest2)));
+  EXPECT_TRUE(frame_reader.IsDoneReading());
+  EXPECT_EQ("Hi", SpdyStringPiece(dest2, SPDY_ARRAYSIZE(dest2)));
+}
+
+TEST(SpdyFrameReaderTest, ReadBytesWithBufferTooSmall) {
+  // Frame data in network byte order.
+  const char kFrameData[] = {
+      0x01,
+  };
+
+  SpdyFrameReader frame_reader(kFrameData, SPDY_ARRAYSIZE(kFrameData));
+  EXPECT_FALSE(frame_reader.IsDoneReading());
+
+  char dest[SPDY_ARRAYSIZE(kFrameData) + 2] = {};
+  EXPECT_FALSE(frame_reader.ReadBytes(&dest, SPDY_ARRAYSIZE(kFrameData) + 1));
+  EXPECT_STREQ("", dest);
+}
+
+}  // namespace spdy
diff --git a/spdy/core/spdy_framer.cc b/spdy/core/spdy_framer.cc
new file mode 100644
index 0000000..fc9cc2e
--- /dev/null
+++ b/spdy/core/spdy_framer.cc
@@ -0,0 +1,1295 @@
+// Copyright (c) 2012 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "net/third_party/quiche/src/spdy/core/spdy_framer.h"
+
+#include <algorithm>
+#include <cstdint>
+#include <iterator>
+#include <list>
+#include <new>
+
+#include "base/logging.h"
+#include "net/third_party/quiche/src/http2/platform/api/http2_macros.h"
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_constants.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_bitmasks.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_frame_builder.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_frame_reader.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_bug_tracker.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_estimate_memory_usage.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_ptr_util.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string_utils.h"
+
+namespace spdy {
+
+namespace {
+
+// Pack parent stream ID and exclusive flag into the format used by HTTP/2
+// headers and priority frames.
+uint32_t PackStreamDependencyValues(bool exclusive,
+                                    SpdyStreamId parent_stream_id) {
+  // Make sure the highest-order bit in the parent stream id is zeroed out.
+  uint32_t parent = parent_stream_id & 0x7fffffff;
+  // Set the one-bit exclusivity flag.
+  uint32_t e_bit = exclusive ? 0x80000000 : 0;
+  return parent | e_bit;
+}
+
+// Used to indicate no flags in a HTTP2 flags field.
+const uint8_t kNoFlags = 0;
+
+// Wire size of pad length field.
+const size_t kPadLengthFieldSize = 1;
+
+// The size of one parameter in SETTINGS frame.
+const size_t kOneSettingParameterSize = 6;
+
+size_t GetUncompressedSerializedLength(const SpdyHeaderBlock& headers) {
+  const size_t num_name_value_pairs_size = sizeof(uint32_t);
+  const size_t length_of_name_size = num_name_value_pairs_size;
+  const size_t length_of_value_size = num_name_value_pairs_size;
+
+  size_t total_length = num_name_value_pairs_size;
+  for (const auto& header : headers) {
+    // We add space for the length of the name and the length of the value as
+    // well as the length of the name and the length of the value.
+    total_length += length_of_name_size + header.first.size() +
+                    length_of_value_size + header.second.size();
+  }
+  return total_length;
+}
+
+// Serializes the flags octet for a given SpdyHeadersIR.
+uint8_t SerializeHeaderFrameFlags(const SpdyHeadersIR& header_ir,
+                                  const bool end_headers) {
+  uint8_t flags = 0;
+  if (header_ir.fin()) {
+    flags |= CONTROL_FLAG_FIN;
+  }
+  if (end_headers) {
+    flags |= HEADERS_FLAG_END_HEADERS;
+  }
+  if (header_ir.padded()) {
+    flags |= HEADERS_FLAG_PADDED;
+  }
+  if (header_ir.has_priority()) {
+    flags |= HEADERS_FLAG_PRIORITY;
+  }
+  return flags;
+}
+
+// Serializes the flags octet for a given SpdyPushPromiseIR.
+uint8_t SerializePushPromiseFrameFlags(const SpdyPushPromiseIR& push_promise_ir,
+                                       const bool end_headers) {
+  uint8_t flags = 0;
+  if (push_promise_ir.padded()) {
+    flags = flags | PUSH_PROMISE_FLAG_PADDED;
+  }
+  if (end_headers) {
+    flags |= PUSH_PROMISE_FLAG_END_PUSH_PROMISE;
+  }
+  return flags;
+}
+
+// Serializes a HEADERS frame from the given SpdyHeadersIR and encoded header
+// block. Does not need or use the SpdyHeaderBlock inside SpdyHeadersIR.
+// Return false if the serialization fails. |encoding| should not be empty.
+bool SerializeHeadersGivenEncoding(const SpdyHeadersIR& headers,
+                                   const SpdyString& encoding,
+                                   const bool end_headers,
+                                   ZeroCopyOutputBuffer* output) {
+  const size_t frame_size =
+      GetHeaderFrameSizeSansBlock(headers) + encoding.size();
+  SpdyFrameBuilder builder(frame_size, output);
+  bool ret = builder.BeginNewFrame(
+      SpdyFrameType::HEADERS, SerializeHeaderFrameFlags(headers, end_headers),
+      headers.stream_id(), frame_size - kFrameHeaderSize);
+  DCHECK_EQ(kFrameHeaderSize, builder.length());
+
+  if (ret && headers.padded()) {
+    ret &= builder.WriteUInt8(headers.padding_payload_len());
+  }
+
+  if (ret && headers.has_priority()) {
+    int weight = ClampHttp2Weight(headers.weight());
+    ret &= builder.WriteUInt32(PackStreamDependencyValues(
+        headers.exclusive(), headers.parent_stream_id()));
+    // Per RFC 7540 section 6.3, serialized weight value is actual value - 1.
+    ret &= builder.WriteUInt8(weight - 1);
+  }
+
+  if (ret) {
+    ret &= builder.WriteBytes(encoding.data(), encoding.size());
+  }
+
+  if (ret && headers.padding_payload_len() > 0) {
+    SpdyString padding(headers.padding_payload_len(), 0);
+    ret &= builder.WriteBytes(padding.data(), padding.length());
+  }
+
+  if (!ret) {
+    DLOG(WARNING) << "Failed to build HEADERS. Not enough space in output";
+  }
+  return ret;
+}
+
+// Serializes a PUSH_PROMISE frame from the given SpdyPushPromiseIR and
+// encoded header block. Does not need or use the SpdyHeaderBlock inside
+// SpdyPushPromiseIR.
+bool SerializePushPromiseGivenEncoding(const SpdyPushPromiseIR& push_promise,
+                                       const SpdyString& encoding,
+                                       const bool end_headers,
+                                       ZeroCopyOutputBuffer* output) {
+  const size_t frame_size =
+      GetPushPromiseFrameSizeSansBlock(push_promise) + encoding.size();
+  SpdyFrameBuilder builder(frame_size, output);
+  bool ok = builder.BeginNewFrame(
+      SpdyFrameType::PUSH_PROMISE,
+      SerializePushPromiseFrameFlags(push_promise, end_headers),
+      push_promise.stream_id(), frame_size - kFrameHeaderSize);
+
+  if (push_promise.padded()) {
+    ok = ok && builder.WriteUInt8(push_promise.padding_payload_len());
+  }
+  ok = ok && builder.WriteUInt32(push_promise.promised_stream_id()) &&
+       builder.WriteBytes(encoding.data(), encoding.size());
+  if (ok && push_promise.padding_payload_len() > 0) {
+    SpdyString padding(push_promise.padding_payload_len(), 0);
+    ok = builder.WriteBytes(padding.data(), padding.length());
+  }
+
+  DLOG_IF(ERROR, !ok) << "Failed to write PUSH_PROMISE encoding, not enough "
+                      << "space in output";
+  return ok;
+}
+
+bool WritePayloadWithContinuation(SpdyFrameBuilder* builder,
+                                  const SpdyString& hpack_encoding,
+                                  SpdyStreamId stream_id,
+                                  SpdyFrameType type,
+                                  int padding_payload_len) {
+  uint8_t end_flag = 0;
+  uint8_t flags = 0;
+  if (type == SpdyFrameType::HEADERS) {
+    end_flag = HEADERS_FLAG_END_HEADERS;
+  } else if (type == SpdyFrameType::PUSH_PROMISE) {
+    end_flag = PUSH_PROMISE_FLAG_END_PUSH_PROMISE;
+  } else {
+    DLOG(FATAL) << "CONTINUATION frames cannot be used with frame type "
+                << FrameTypeToString(type);
+  }
+
+  // Write all the padding payload and as much of the data payload as possible
+  // into the initial frame.
+  size_t bytes_remaining = 0;
+  bytes_remaining = hpack_encoding.size() -
+                    std::min(hpack_encoding.size(),
+                             kHttp2MaxControlFrameSendSize - builder->length() -
+                                 padding_payload_len);
+  bool ret = builder->WriteBytes(&hpack_encoding[0],
+                                 hpack_encoding.size() - bytes_remaining);
+  if (padding_payload_len > 0) {
+    SpdyString padding = SpdyString(padding_payload_len, 0);
+    ret &= builder->WriteBytes(padding.data(), padding.length());
+  }
+
+  // Tack on CONTINUATION frames for the overflow.
+  while (bytes_remaining > 0 && ret) {
+    size_t bytes_to_write =
+        std::min(bytes_remaining,
+                 kHttp2MaxControlFrameSendSize - kContinuationFrameMinimumSize);
+    // Write CONTINUATION frame prefix.
+    if (bytes_remaining == bytes_to_write) {
+      flags |= end_flag;
+    }
+    ret &= builder->BeginNewFrame(SpdyFrameType::CONTINUATION, flags, stream_id,
+                                  bytes_to_write);
+    // Write payload fragment.
+    ret &= builder->WriteBytes(
+        &hpack_encoding[hpack_encoding.size() - bytes_remaining],
+        bytes_to_write);
+    bytes_remaining -= bytes_to_write;
+  }
+  return ret;
+}
+
+void SerializeDataBuilderHelper(const SpdyDataIR& data_ir,
+                                uint8_t* flags,
+                                int* num_padding_fields,
+                                size_t* size_with_padding) {
+  if (data_ir.fin()) {
+    *flags = DATA_FLAG_FIN;
+  }
+
+  if (data_ir.padded()) {
+    *flags = *flags | DATA_FLAG_PADDED;
+    ++*num_padding_fields;
+  }
+
+  *size_with_padding = *num_padding_fields + data_ir.data_len() +
+                       data_ir.padding_payload_len() + kDataFrameMinimumSize;
+}
+
+void SerializeDataFrameHeaderWithPaddingLengthFieldBuilderHelper(
+    const SpdyDataIR& data_ir,
+    uint8_t* flags,
+    size_t* frame_size,
+    size_t* num_padding_fields) {
+  *flags = DATA_FLAG_NONE;
+  if (data_ir.fin()) {
+    *flags = DATA_FLAG_FIN;
+  }
+
+  *frame_size = kDataFrameMinimumSize;
+  if (data_ir.padded()) {
+    *flags = *flags | DATA_FLAG_PADDED;
+    ++(*num_padding_fields);
+    *frame_size = *frame_size + *num_padding_fields;
+  }
+}
+
+void SerializeSettingsBuilderHelper(const SpdySettingsIR& settings,
+                                    uint8_t* flags,
+                                    const SettingsMap* values,
+                                    size_t* size) {
+  if (settings.is_ack()) {
+    *flags = *flags | SETTINGS_FLAG_ACK;
+  }
+  *size =
+      kSettingsFrameMinimumSize + (values->size() * kOneSettingParameterSize);
+}
+
+void SerializeAltSvcBuilderHelper(const SpdyAltSvcIR& altsvc_ir,
+                                  SpdyString* value,
+                                  size_t* size) {
+  *size = kGetAltSvcFrameMinimumSize;
+  *size = *size + altsvc_ir.origin().length();
+  *value = SpdyAltSvcWireFormat::SerializeHeaderFieldValue(
+      altsvc_ir.altsvc_vector());
+  *size = *size + value->length();
+}
+
+}  // namespace
+
+SpdyFramer::SpdyFramer(CompressionOption option)
+    : debug_visitor_(nullptr), compression_option_(option) {
+  static_assert(kHttp2MaxControlFrameSendSize <= kHttp2DefaultFrameSizeLimit,
+                "Our send limit should be at most our receive limit.");
+}
+
+SpdyFramer::~SpdyFramer() = default;
+
+void SpdyFramer::set_debug_visitor(
+    SpdyFramerDebugVisitorInterface* debug_visitor) {
+  debug_visitor_ = debug_visitor;
+}
+
+SpdyFramer::SpdyFrameIterator::SpdyFrameIterator(SpdyFramer* framer)
+    : framer_(framer), is_first_frame_(true), has_next_frame_(true) {}
+
+SpdyFramer::SpdyFrameIterator::~SpdyFrameIterator() = default;
+
+size_t SpdyFramer::SpdyFrameIterator::NextFrame(ZeroCopyOutputBuffer* output) {
+  const SpdyFrameIR& frame_ir = GetIR();
+  if (!has_next_frame_) {
+    SPDY_BUG << "SpdyFramer::SpdyFrameIterator::NextFrame called without "
+             << "a next frame.";
+    return false;
+  }
+
+  const size_t size_without_block =
+      is_first_frame_ ? GetFrameSizeSansBlock() : kContinuationFrameMinimumSize;
+  auto encoding = SpdyMakeUnique<SpdyString>();
+  encoder_->Next(kHttp2MaxControlFrameSendSize - size_without_block,
+                 encoding.get());
+  has_next_frame_ = encoder_->HasNext();
+
+  if (framer_->debug_visitor_ != nullptr) {
+    const auto& header_block_frame_ir =
+        down_cast<const SpdyFrameWithHeaderBlockIR&>(frame_ir);
+    const size_t header_list_size =
+        GetUncompressedSerializedLength(header_block_frame_ir.header_block());
+    framer_->debug_visitor_->OnSendCompressedFrame(
+        frame_ir.stream_id(),
+        is_first_frame_ ? frame_ir.frame_type() : SpdyFrameType::CONTINUATION,
+        header_list_size, size_without_block + encoding->size());
+  }
+
+  const size_t free_bytes_before = output->BytesFree();
+  bool ok = false;
+  if (is_first_frame_) {
+    is_first_frame_ = false;
+    ok = SerializeGivenEncoding(*encoding, output);
+  } else {
+    SpdyContinuationIR continuation_ir(frame_ir.stream_id());
+    continuation_ir.take_encoding(std::move(encoding));
+    continuation_ir.set_end_headers(!has_next_frame_);
+    ok = framer_->SerializeContinuation(continuation_ir, output);
+  }
+  return ok ? free_bytes_before - output->BytesFree() : 0;
+}
+
+bool SpdyFramer::SpdyFrameIterator::HasNextFrame() const {
+  return has_next_frame_;
+}
+
+SpdyFramer::SpdyHeaderFrameIterator::SpdyHeaderFrameIterator(
+    SpdyFramer* framer,
+    std::unique_ptr<const SpdyHeadersIR> headers_ir)
+    : SpdyFrameIterator(framer), headers_ir_(std::move(headers_ir)) {
+  SetEncoder(headers_ir_.get());
+}
+
+SpdyFramer::SpdyHeaderFrameIterator::~SpdyHeaderFrameIterator() = default;
+
+const SpdyFrameIR& SpdyFramer::SpdyHeaderFrameIterator::GetIR() const {
+  return *(headers_ir_.get());
+}
+
+size_t SpdyFramer::SpdyHeaderFrameIterator::GetFrameSizeSansBlock() const {
+  return GetHeaderFrameSizeSansBlock(*headers_ir_);
+}
+
+bool SpdyFramer::SpdyHeaderFrameIterator::SerializeGivenEncoding(
+    const SpdyString& encoding,
+    ZeroCopyOutputBuffer* output) const {
+  return SerializeHeadersGivenEncoding(*headers_ir_, encoding,
+                                       !has_next_frame(), output);
+}
+
+SpdyFramer::SpdyPushPromiseFrameIterator::SpdyPushPromiseFrameIterator(
+    SpdyFramer* framer,
+    std::unique_ptr<const SpdyPushPromiseIR> push_promise_ir)
+    : SpdyFrameIterator(framer), push_promise_ir_(std::move(push_promise_ir)) {
+  SetEncoder(push_promise_ir_.get());
+}
+
+SpdyFramer::SpdyPushPromiseFrameIterator::~SpdyPushPromiseFrameIterator() =
+    default;
+
+const SpdyFrameIR& SpdyFramer::SpdyPushPromiseFrameIterator::GetIR() const {
+  return *(push_promise_ir_.get());
+}
+
+size_t SpdyFramer::SpdyPushPromiseFrameIterator::GetFrameSizeSansBlock() const {
+  return GetPushPromiseFrameSizeSansBlock(*push_promise_ir_);
+}
+
+bool SpdyFramer::SpdyPushPromiseFrameIterator::SerializeGivenEncoding(
+    const SpdyString& encoding,
+    ZeroCopyOutputBuffer* output) const {
+  return SerializePushPromiseGivenEncoding(*push_promise_ir_, encoding,
+                                           !has_next_frame(), output);
+}
+
+SpdyFramer::SpdyControlFrameIterator::SpdyControlFrameIterator(
+    SpdyFramer* framer,
+    std::unique_ptr<const SpdyFrameIR> frame_ir)
+    : framer_(framer), frame_ir_(std::move(frame_ir)) {}
+
+SpdyFramer::SpdyControlFrameIterator::~SpdyControlFrameIterator() = default;
+
+size_t SpdyFramer::SpdyControlFrameIterator::NextFrame(
+    ZeroCopyOutputBuffer* output) {
+  size_t size_written = framer_->SerializeFrame(*frame_ir_, output);
+  has_next_frame_ = false;
+  return size_written;
+}
+
+bool SpdyFramer::SpdyControlFrameIterator::HasNextFrame() const {
+  return has_next_frame_;
+}
+
+const SpdyFrameIR& SpdyFramer::SpdyControlFrameIterator::GetIR() const {
+  return *(frame_ir_.get());
+}
+
+// TODO(yasong): remove all the down_casts.
+std::unique_ptr<SpdyFrameSequence> SpdyFramer::CreateIterator(
+    SpdyFramer* framer,
+    std::unique_ptr<const SpdyFrameIR> frame_ir) {
+  switch (frame_ir->frame_type()) {
+    case SpdyFrameType::HEADERS: {
+      return SpdyMakeUnique<SpdyHeaderFrameIterator>(
+          framer,
+          SpdyWrapUnique(down_cast<const SpdyHeadersIR*>(frame_ir.release())));
+    }
+    case SpdyFrameType::PUSH_PROMISE: {
+      return SpdyMakeUnique<SpdyPushPromiseFrameIterator>(
+          framer, SpdyWrapUnique(
+                      down_cast<const SpdyPushPromiseIR*>(frame_ir.release())));
+    }
+    case SpdyFrameType::DATA: {
+      DVLOG(1) << "Serialize a stream end DATA frame for VTL";
+      HTTP2_FALLTHROUGH;
+    }
+    default: {
+      return SpdyMakeUnique<SpdyControlFrameIterator>(framer,
+                                                      std::move(frame_ir));
+    }
+  }
+}
+
+SpdySerializedFrame SpdyFramer::SerializeData(const SpdyDataIR& data_ir) {
+  uint8_t flags = DATA_FLAG_NONE;
+  int num_padding_fields = 0;
+  size_t size_with_padding = 0;
+  SerializeDataBuilderHelper(data_ir, &flags, &num_padding_fields,
+                             &size_with_padding);
+
+  SpdyFrameBuilder builder(size_with_padding);
+  builder.BeginNewFrame(SpdyFrameType::DATA, flags, data_ir.stream_id());
+  if (data_ir.padded()) {
+    builder.WriteUInt8(data_ir.padding_payload_len() & 0xff);
+  }
+  builder.WriteBytes(data_ir.data(), data_ir.data_len());
+  if (data_ir.padding_payload_len() > 0) {
+    SpdyString padding(data_ir.padding_payload_len(), 0);
+    builder.WriteBytes(padding.data(), padding.length());
+  }
+  DCHECK_EQ(size_with_padding, builder.length());
+  return builder.take();
+}
+
+SpdySerializedFrame SpdyFramer::SerializeDataFrameHeaderWithPaddingLengthField(
+    const SpdyDataIR& data_ir) {
+  uint8_t flags = DATA_FLAG_NONE;
+  size_t frame_size = 0;
+  size_t num_padding_fields = 0;
+  SerializeDataFrameHeaderWithPaddingLengthFieldBuilderHelper(
+      data_ir, &flags, &frame_size, &num_padding_fields);
+
+  SpdyFrameBuilder builder(frame_size);
+  builder.BeginNewFrame(
+      SpdyFrameType::DATA, flags, data_ir.stream_id(),
+      num_padding_fields + data_ir.data_len() + data_ir.padding_payload_len());
+  if (data_ir.padded()) {
+    builder.WriteUInt8(data_ir.padding_payload_len() & 0xff);
+  }
+  DCHECK_EQ(frame_size, builder.length());
+  return builder.take();
+}
+
+SpdySerializedFrame SpdyFramer::SerializeRstStream(
+    const SpdyRstStreamIR& rst_stream) const {
+  size_t expected_length = kRstStreamFrameSize;
+  SpdyFrameBuilder builder(expected_length);
+
+  builder.BeginNewFrame(SpdyFrameType::RST_STREAM, 0, rst_stream.stream_id());
+
+  builder.WriteUInt32(rst_stream.error_code());
+
+  DCHECK_EQ(expected_length, builder.length());
+  return builder.take();
+}
+
+SpdySerializedFrame SpdyFramer::SerializeSettings(
+    const SpdySettingsIR& settings) const {
+  uint8_t flags = 0;
+  // Size, in bytes, of this SETTINGS frame.
+  size_t size = 0;
+  const SettingsMap* values = &(settings.values());
+  SerializeSettingsBuilderHelper(settings, &flags, values, &size);
+  SpdyFrameBuilder builder(size);
+  builder.BeginNewFrame(SpdyFrameType::SETTINGS, flags, 0);
+
+  // If this is an ACK, payload should be empty.
+  if (settings.is_ack()) {
+    return builder.take();
+  }
+
+  DCHECK_EQ(kSettingsFrameMinimumSize, builder.length());
+  for (auto it = values->begin(); it != values->end(); ++it) {
+    int setting_id = it->first;
+    DCHECK_GE(setting_id, 0);
+    builder.WriteUInt16(static_cast<SpdySettingsId>(setting_id));
+    builder.WriteUInt32(it->second);
+  }
+  DCHECK_EQ(size, builder.length());
+  return builder.take();
+}
+
+SpdySerializedFrame SpdyFramer::SerializePing(const SpdyPingIR& ping) const {
+  SpdyFrameBuilder builder(kPingFrameSize);
+  uint8_t flags = 0;
+  if (ping.is_ack()) {
+    flags |= PING_FLAG_ACK;
+  }
+  builder.BeginNewFrame(SpdyFrameType::PING, flags, 0);
+  builder.WriteUInt64(ping.id());
+  DCHECK_EQ(kPingFrameSize, builder.length());
+  return builder.take();
+}
+
+SpdySerializedFrame SpdyFramer::SerializeGoAway(
+    const SpdyGoAwayIR& goaway) const {
+  // Compute the output buffer size, take opaque data into account.
+  size_t expected_length = kGoawayFrameMinimumSize;
+  expected_length += goaway.description().size();
+  SpdyFrameBuilder builder(expected_length);
+
+  // Serialize the GOAWAY frame.
+  builder.BeginNewFrame(SpdyFrameType::GOAWAY, 0, 0);
+
+  // GOAWAY frames specify the last good stream id.
+  builder.WriteUInt32(goaway.last_good_stream_id());
+
+  // GOAWAY frames also specify the error code.
+  builder.WriteUInt32(goaway.error_code());
+
+  // GOAWAY frames may also specify opaque data.
+  if (!goaway.description().empty()) {
+    builder.WriteBytes(goaway.description().data(),
+                       goaway.description().size());
+  }
+
+  DCHECK_EQ(expected_length, builder.length());
+  return builder.take();
+}
+
+void SpdyFramer::SerializeHeadersBuilderHelper(const SpdyHeadersIR& headers,
+                                               uint8_t* flags,
+                                               size_t* size,
+                                               SpdyString* hpack_encoding,
+                                               int* weight,
+                                               size_t* length_field) {
+  if (headers.fin()) {
+    *flags = *flags | CONTROL_FLAG_FIN;
+  }
+  // This will get overwritten if we overflow into a CONTINUATION frame.
+  *flags = *flags | HEADERS_FLAG_END_HEADERS;
+  if (headers.has_priority()) {
+    *flags = *flags | HEADERS_FLAG_PRIORITY;
+  }
+  if (headers.padded()) {
+    *flags = *flags | HEADERS_FLAG_PADDED;
+  }
+
+  *size = kHeadersFrameMinimumSize;
+
+  if (headers.padded()) {
+    *size = *size + kPadLengthFieldSize;
+    *size = *size + headers.padding_payload_len();
+  }
+
+  if (headers.has_priority()) {
+    *weight = ClampHttp2Weight(headers.weight());
+    *size = *size + 5;
+  }
+
+  GetHpackEncoder()->EncodeHeaderSet(headers.header_block(), hpack_encoding);
+  *size = *size + hpack_encoding->size();
+  if (*size > kHttp2MaxControlFrameSendSize) {
+    *size = *size + GetNumberRequiredContinuationFrames(*size) *
+                        kContinuationFrameMinimumSize;
+    *flags = *flags & ~HEADERS_FLAG_END_HEADERS;
+  }
+  // Compute frame length field.
+  if (headers.padded()) {
+    *length_field = *length_field + kPadLengthFieldSize;
+  }
+  if (headers.has_priority()) {
+    *length_field = *length_field + 4;  // Dependency field.
+    *length_field = *length_field + 1;  // Weight field.
+  }
+  *length_field = *length_field + headers.padding_payload_len();
+  *length_field = *length_field + hpack_encoding->size();
+  // If the HEADERS frame with payload would exceed the max frame size, then
+  // WritePayloadWithContinuation() will serialize CONTINUATION frames as
+  // necessary.
+  *length_field =
+      std::min(*length_field, kHttp2MaxControlFrameSendSize - kFrameHeaderSize);
+}
+
+SpdySerializedFrame SpdyFramer::SerializeHeaders(const SpdyHeadersIR& headers) {
+  uint8_t flags = 0;
+  // The size of this frame, including padding (if there is any) and
+  // variable-length header block.
+  size_t size = 0;
+  SpdyString hpack_encoding;
+  int weight = 0;
+  size_t length_field = 0;
+  SerializeHeadersBuilderHelper(headers, &flags, &size, &hpack_encoding,
+                                &weight, &length_field);
+
+  SpdyFrameBuilder builder(size);
+  builder.BeginNewFrame(SpdyFrameType::HEADERS, flags, headers.stream_id(),
+                        length_field);
+
+  DCHECK_EQ(kHeadersFrameMinimumSize, builder.length());
+
+  int padding_payload_len = 0;
+  if (headers.padded()) {
+    builder.WriteUInt8(headers.padding_payload_len());
+    padding_payload_len = headers.padding_payload_len();
+  }
+  if (headers.has_priority()) {
+    builder.WriteUInt32(PackStreamDependencyValues(headers.exclusive(),
+                                                   headers.parent_stream_id()));
+    // Per RFC 7540 section 6.3, serialized weight value is actual value - 1.
+    builder.WriteUInt8(weight - 1);
+  }
+  WritePayloadWithContinuation(&builder, hpack_encoding, headers.stream_id(),
+                               SpdyFrameType::HEADERS, padding_payload_len);
+
+  if (debug_visitor_) {
+    const size_t header_list_size =
+        GetUncompressedSerializedLength(headers.header_block());
+    debug_visitor_->OnSendCompressedFrame(headers.stream_id(),
+                                          SpdyFrameType::HEADERS,
+                                          header_list_size, builder.length());
+  }
+
+  return builder.take();
+}
+
+SpdySerializedFrame SpdyFramer::SerializeWindowUpdate(
+    const SpdyWindowUpdateIR& window_update) {
+  SpdyFrameBuilder builder(kWindowUpdateFrameSize);
+  builder.BeginNewFrame(SpdyFrameType::WINDOW_UPDATE, kNoFlags,
+                        window_update.stream_id());
+  builder.WriteUInt32(window_update.delta());
+  DCHECK_EQ(kWindowUpdateFrameSize, builder.length());
+  return builder.take();
+}
+
+void SpdyFramer::SerializePushPromiseBuilderHelper(
+    const SpdyPushPromiseIR& push_promise,
+    uint8_t* flags,
+    SpdyString* hpack_encoding,
+    size_t* size) {
+  *flags = 0;
+  // This will get overwritten if we overflow into a CONTINUATION frame.
+  *flags = *flags | PUSH_PROMISE_FLAG_END_PUSH_PROMISE;
+  // The size of this frame, including variable-length name-value block.
+  *size = kPushPromiseFrameMinimumSize;
+
+  if (push_promise.padded()) {
+    *flags = *flags | PUSH_PROMISE_FLAG_PADDED;
+    *size = *size + kPadLengthFieldSize;
+    *size = *size + push_promise.padding_payload_len();
+  }
+
+  GetHpackEncoder()->EncodeHeaderSet(push_promise.header_block(),
+                                     hpack_encoding);
+  *size = *size + hpack_encoding->size();
+  if (*size > kHttp2MaxControlFrameSendSize) {
+    *size = *size + GetNumberRequiredContinuationFrames(*size) *
+                        kContinuationFrameMinimumSize;
+    *flags = *flags & ~PUSH_PROMISE_FLAG_END_PUSH_PROMISE;
+  }
+}
+
+SpdySerializedFrame SpdyFramer::SerializePushPromise(
+    const SpdyPushPromiseIR& push_promise) {
+  uint8_t flags = 0;
+  size_t size = 0;
+  SpdyString hpack_encoding;
+  SerializePushPromiseBuilderHelper(push_promise, &flags, &hpack_encoding,
+                                    &size);
+
+  SpdyFrameBuilder builder(size);
+  size_t length =
+      std::min(size, kHttp2MaxControlFrameSendSize) - kFrameHeaderSize;
+  builder.BeginNewFrame(SpdyFrameType::PUSH_PROMISE, flags,
+                        push_promise.stream_id(), length);
+  int padding_payload_len = 0;
+  if (push_promise.padded()) {
+    builder.WriteUInt8(push_promise.padding_payload_len());
+    builder.WriteUInt32(push_promise.promised_stream_id());
+    DCHECK_EQ(kPushPromiseFrameMinimumSize + kPadLengthFieldSize,
+              builder.length());
+
+    padding_payload_len = push_promise.padding_payload_len();
+  } else {
+    builder.WriteUInt32(push_promise.promised_stream_id());
+    DCHECK_EQ(kPushPromiseFrameMinimumSize, builder.length());
+  }
+
+  WritePayloadWithContinuation(
+      &builder, hpack_encoding, push_promise.stream_id(),
+      SpdyFrameType::PUSH_PROMISE, padding_payload_len);
+
+  if (debug_visitor_) {
+    const size_t header_list_size =
+        GetUncompressedSerializedLength(push_promise.header_block());
+    debug_visitor_->OnSendCompressedFrame(push_promise.stream_id(),
+                                          SpdyFrameType::PUSH_PROMISE,
+                                          header_list_size, builder.length());
+  }
+
+  return builder.take();
+}
+
+SpdySerializedFrame SpdyFramer::SerializeContinuation(
+    const SpdyContinuationIR& continuation) const {
+  const SpdyString& encoding = continuation.encoding();
+  size_t frame_size = kContinuationFrameMinimumSize + encoding.size();
+  SpdyFrameBuilder builder(frame_size);
+  uint8_t flags = continuation.end_headers() ? HEADERS_FLAG_END_HEADERS : 0;
+  builder.BeginNewFrame(SpdyFrameType::CONTINUATION, flags,
+                        continuation.stream_id());
+  DCHECK_EQ(kFrameHeaderSize, builder.length());
+
+  builder.WriteBytes(encoding.data(), encoding.size());
+  return builder.take();
+}
+
+SpdySerializedFrame SpdyFramer::SerializeAltSvc(const SpdyAltSvcIR& altsvc_ir) {
+  SpdyString value;
+  size_t size = 0;
+  SerializeAltSvcBuilderHelper(altsvc_ir, &value, &size);
+  SpdyFrameBuilder builder(size);
+  builder.BeginNewFrame(SpdyFrameType::ALTSVC, kNoFlags, altsvc_ir.stream_id());
+
+  builder.WriteUInt16(altsvc_ir.origin().length());
+  builder.WriteBytes(altsvc_ir.origin().data(), altsvc_ir.origin().length());
+  builder.WriteBytes(value.data(), value.length());
+  DCHECK_LT(kGetAltSvcFrameMinimumSize, builder.length());
+  return builder.take();
+}
+
+SpdySerializedFrame SpdyFramer::SerializePriority(
+    const SpdyPriorityIR& priority) const {
+  SpdyFrameBuilder builder(kPriorityFrameSize);
+  builder.BeginNewFrame(SpdyFrameType::PRIORITY, kNoFlags,
+                        priority.stream_id());
+
+  builder.WriteUInt32(PackStreamDependencyValues(priority.exclusive(),
+                                                 priority.parent_stream_id()));
+  // Per RFC 7540 section 6.3, serialized weight value is actual value - 1.
+  builder.WriteUInt8(priority.weight() - 1);
+  DCHECK_EQ(kPriorityFrameSize, builder.length());
+  return builder.take();
+}
+
+SpdySerializedFrame SpdyFramer::SerializeUnknown(
+    const SpdyUnknownIR& unknown) const {
+  const size_t total_size = kFrameHeaderSize + unknown.payload().size();
+  SpdyFrameBuilder builder(total_size);
+  builder.BeginNewUncheckedFrame(unknown.type(), unknown.flags(),
+                                 unknown.stream_id(), unknown.length());
+  builder.WriteBytes(unknown.payload().data(), unknown.payload().size());
+  return builder.take();
+}
+
+namespace {
+
+class FrameSerializationVisitor : public SpdyFrameVisitor {
+ public:
+  explicit FrameSerializationVisitor(SpdyFramer* framer)
+      : framer_(framer), frame_() {}
+  ~FrameSerializationVisitor() override = default;
+
+  SpdySerializedFrame ReleaseSerializedFrame() { return std::move(frame_); }
+
+  void VisitData(const SpdyDataIR& data) override {
+    frame_ = framer_->SerializeData(data);
+  }
+  void VisitRstStream(const SpdyRstStreamIR& rst_stream) override {
+    frame_ = framer_->SerializeRstStream(rst_stream);
+  }
+  void VisitSettings(const SpdySettingsIR& settings) override {
+    frame_ = framer_->SerializeSettings(settings);
+  }
+  void VisitPing(const SpdyPingIR& ping) override {
+    frame_ = framer_->SerializePing(ping);
+  }
+  void VisitGoAway(const SpdyGoAwayIR& goaway) override {
+    frame_ = framer_->SerializeGoAway(goaway);
+  }
+  void VisitHeaders(const SpdyHeadersIR& headers) override {
+    frame_ = framer_->SerializeHeaders(headers);
+  }
+  void VisitWindowUpdate(const SpdyWindowUpdateIR& window_update) override {
+    frame_ = framer_->SerializeWindowUpdate(window_update);
+  }
+  void VisitPushPromise(const SpdyPushPromiseIR& push_promise) override {
+    frame_ = framer_->SerializePushPromise(push_promise);
+  }
+  void VisitContinuation(const SpdyContinuationIR& continuation) override {
+    frame_ = framer_->SerializeContinuation(continuation);
+  }
+  void VisitAltSvc(const SpdyAltSvcIR& altsvc) override {
+    frame_ = framer_->SerializeAltSvc(altsvc);
+  }
+  void VisitPriority(const SpdyPriorityIR& priority) override {
+    frame_ = framer_->SerializePriority(priority);
+  }
+  void VisitUnknown(const SpdyUnknownIR& unknown) override {
+    frame_ = framer_->SerializeUnknown(unknown);
+  }
+
+ private:
+  SpdyFramer* framer_;
+  SpdySerializedFrame frame_;
+};
+
+// TODO(diannahu): Use also in frame serialization.
+class FlagsSerializationVisitor : public SpdyFrameVisitor {
+ public:
+  void VisitData(const SpdyDataIR& data) override {
+    flags_ = DATA_FLAG_NONE;
+    if (data.fin()) {
+      flags_ |= DATA_FLAG_FIN;
+    }
+    if (data.padded()) {
+      flags_ |= DATA_FLAG_PADDED;
+    }
+  }
+
+  void VisitRstStream(const SpdyRstStreamIR& rst_stream) override {
+    flags_ = kNoFlags;
+  }
+
+  void VisitSettings(const SpdySettingsIR& settings) override {
+    flags_ = kNoFlags;
+    if (settings.is_ack()) {
+      flags_ |= SETTINGS_FLAG_ACK;
+    }
+  }
+
+  void VisitPing(const SpdyPingIR& ping) override {
+    flags_ = kNoFlags;
+    if (ping.is_ack()) {
+      flags_ |= PING_FLAG_ACK;
+    }
+  }
+
+  void VisitGoAway(const SpdyGoAwayIR& goaway) override { flags_ = kNoFlags; }
+
+  // TODO(diannahu): The END_HEADERS flag is incorrect for HEADERS that require
+  //     CONTINUATION frames.
+  void VisitHeaders(const SpdyHeadersIR& headers) override {
+    flags_ = HEADERS_FLAG_END_HEADERS;
+    if (headers.fin()) {
+      flags_ |= CONTROL_FLAG_FIN;
+    }
+    if (headers.padded()) {
+      flags_ |= HEADERS_FLAG_PADDED;
+    }
+    if (headers.has_priority()) {
+      flags_ |= HEADERS_FLAG_PRIORITY;
+    }
+  }
+
+  void VisitWindowUpdate(const SpdyWindowUpdateIR& window_update) override {
+    flags_ = kNoFlags;
+  }
+
+  // TODO(diannahu): The END_PUSH_PROMISE flag is incorrect for PUSH_PROMISEs
+  //     that require CONTINUATION frames.
+  void VisitPushPromise(const SpdyPushPromiseIR& push_promise) override {
+    flags_ = PUSH_PROMISE_FLAG_END_PUSH_PROMISE;
+    if (push_promise.padded()) {
+      flags_ |= PUSH_PROMISE_FLAG_PADDED;
+    }
+  }
+
+  // TODO(diannahu): The END_HEADERS flag is incorrect for CONTINUATIONs that
+  //     require CONTINUATION frames.
+  void VisitContinuation(const SpdyContinuationIR& continuation) override {
+    flags_ = HEADERS_FLAG_END_HEADERS;
+  }
+
+  void VisitAltSvc(const SpdyAltSvcIR& altsvc) override { flags_ = kNoFlags; }
+
+  void VisitPriority(const SpdyPriorityIR& priority) override {
+    flags_ = kNoFlags;
+  }
+
+  uint8_t flags() const { return flags_; }
+
+ private:
+  uint8_t flags_ = kNoFlags;
+};
+
+}  // namespace
+
+SpdySerializedFrame SpdyFramer::SerializeFrame(const SpdyFrameIR& frame) {
+  FrameSerializationVisitor visitor(this);
+  frame.Visit(&visitor);
+  return visitor.ReleaseSerializedFrame();
+}
+
+uint8_t SpdyFramer::GetSerializedFlags(const SpdyFrameIR& frame) {
+  FlagsSerializationVisitor visitor;
+  frame.Visit(&visitor);
+  return visitor.flags();
+}
+
+bool SpdyFramer::SerializeData(const SpdyDataIR& data_ir,
+                               ZeroCopyOutputBuffer* output) const {
+  uint8_t flags = DATA_FLAG_NONE;
+  int num_padding_fields = 0;
+  size_t size_with_padding = 0;
+  SerializeDataBuilderHelper(data_ir, &flags, &num_padding_fields,
+                             &size_with_padding);
+  SpdyFrameBuilder builder(size_with_padding, output);
+
+  bool ok =
+      builder.BeginNewFrame(SpdyFrameType::DATA, flags, data_ir.stream_id());
+
+  if (data_ir.padded()) {
+    ok = ok && builder.WriteUInt8(data_ir.padding_payload_len() & 0xff);
+  }
+
+  ok = ok && builder.WriteBytes(data_ir.data(), data_ir.data_len());
+  if (data_ir.padding_payload_len() > 0) {
+    SpdyString padding;
+    padding = SpdyString(data_ir.padding_payload_len(), 0);
+    ok = ok && builder.WriteBytes(padding.data(), padding.length());
+  }
+  DCHECK_EQ(size_with_padding, builder.length());
+  return ok;
+}
+
+bool SpdyFramer::SerializeDataFrameHeaderWithPaddingLengthField(
+    const SpdyDataIR& data_ir,
+    ZeroCopyOutputBuffer* output) const {
+  uint8_t flags = DATA_FLAG_NONE;
+  size_t frame_size = 0;
+  size_t num_padding_fields = 0;
+  SerializeDataFrameHeaderWithPaddingLengthFieldBuilderHelper(
+      data_ir, &flags, &frame_size, &num_padding_fields);
+
+  SpdyFrameBuilder builder(frame_size, output);
+  bool ok = true;
+  ok = ok &&
+       builder.BeginNewFrame(SpdyFrameType::DATA, flags, data_ir.stream_id(),
+                             num_padding_fields + data_ir.data_len() +
+                                 data_ir.padding_payload_len());
+  if (data_ir.padded()) {
+    ok = ok && builder.WriteUInt8(data_ir.padding_payload_len() & 0xff);
+  }
+  DCHECK_EQ(frame_size, builder.length());
+  return ok;
+}
+
+bool SpdyFramer::SerializeRstStream(const SpdyRstStreamIR& rst_stream,
+                                    ZeroCopyOutputBuffer* output) const {
+  size_t expected_length = kRstStreamFrameSize;
+  SpdyFrameBuilder builder(expected_length, output);
+  bool ok = builder.BeginNewFrame(SpdyFrameType::RST_STREAM, 0,
+                                  rst_stream.stream_id());
+  ok = ok && builder.WriteUInt32(rst_stream.error_code());
+
+  DCHECK_EQ(expected_length, builder.length());
+  return ok;
+}
+
+bool SpdyFramer::SerializeSettings(const SpdySettingsIR& settings,
+                                   ZeroCopyOutputBuffer* output) const {
+  uint8_t flags = 0;
+  // Size, in bytes, of this SETTINGS frame.
+  size_t size = 0;
+  const SettingsMap* values = &(settings.values());
+  SerializeSettingsBuilderHelper(settings, &flags, values, &size);
+  SpdyFrameBuilder builder(size, output);
+  bool ok = builder.BeginNewFrame(SpdyFrameType::SETTINGS, flags, 0);
+
+  // If this is an ACK, payload should be empty.
+  if (settings.is_ack()) {
+    return ok;
+  }
+
+  DCHECK_EQ(kSettingsFrameMinimumSize, builder.length());
+  for (auto it = values->begin(); it != values->end(); ++it) {
+    int setting_id = it->first;
+    DCHECK_GE(setting_id, 0);
+    ok = ok && builder.WriteUInt16(static_cast<SpdySettingsId>(setting_id)) &&
+         builder.WriteUInt32(it->second);
+  }
+  DCHECK_EQ(size, builder.length());
+  return ok;
+}
+
+bool SpdyFramer::SerializePing(const SpdyPingIR& ping,
+                               ZeroCopyOutputBuffer* output) const {
+  SpdyFrameBuilder builder(kPingFrameSize, output);
+  uint8_t flags = 0;
+  if (ping.is_ack()) {
+    flags |= PING_FLAG_ACK;
+  }
+  bool ok = builder.BeginNewFrame(SpdyFrameType::PING, flags, 0);
+  ok = ok && builder.WriteUInt64(ping.id());
+  DCHECK_EQ(kPingFrameSize, builder.length());
+  return ok;
+}
+
+bool SpdyFramer::SerializeGoAway(const SpdyGoAwayIR& goaway,
+                                 ZeroCopyOutputBuffer* output) const {
+  // Compute the output buffer size, take opaque data into account.
+  size_t expected_length = kGoawayFrameMinimumSize;
+  expected_length += goaway.description().size();
+  SpdyFrameBuilder builder(expected_length, output);
+
+  // Serialize the GOAWAY frame.
+  bool ok = builder.BeginNewFrame(SpdyFrameType::GOAWAY, 0, 0);
+
+  // GOAWAY frames specify the last good stream id.
+  ok = ok && builder.WriteUInt32(goaway.last_good_stream_id()) &&
+       // GOAWAY frames also specify the error status code.
+       builder.WriteUInt32(goaway.error_code());
+
+  // GOAWAY frames may also specify opaque data.
+  if (!goaway.description().empty()) {
+    ok = ok && builder.WriteBytes(goaway.description().data(),
+                                  goaway.description().size());
+  }
+
+  DCHECK_EQ(expected_length, builder.length());
+  return ok;
+}
+
+bool SpdyFramer::SerializeHeaders(const SpdyHeadersIR& headers,
+                                  ZeroCopyOutputBuffer* output) {
+  uint8_t flags = 0;
+  // The size of this frame, including padding (if there is any) and
+  // variable-length header block.
+  size_t size = 0;
+  SpdyString hpack_encoding;
+  int weight = 0;
+  size_t length_field = 0;
+  SerializeHeadersBuilderHelper(headers, &flags, &size, &hpack_encoding,
+                                &weight, &length_field);
+
+  bool ok = true;
+  SpdyFrameBuilder builder(size, output);
+  ok = ok && builder.BeginNewFrame(SpdyFrameType::HEADERS, flags,
+                                   headers.stream_id(), length_field);
+  DCHECK_EQ(kHeadersFrameMinimumSize, builder.length());
+
+  int padding_payload_len = 0;
+  if (headers.padded()) {
+    ok = ok && builder.WriteUInt8(headers.padding_payload_len());
+    padding_payload_len = headers.padding_payload_len();
+  }
+  if (headers.has_priority()) {
+    ok = ok &&
+         builder.WriteUInt32(PackStreamDependencyValues(
+             headers.exclusive(), headers.parent_stream_id())) &&
+         // Per RFC 7540 section 6.3, serialized weight value is weight - 1.
+         builder.WriteUInt8(weight - 1);
+  }
+  ok = ok && WritePayloadWithContinuation(
+                 &builder, hpack_encoding, headers.stream_id(),
+                 SpdyFrameType::HEADERS, padding_payload_len);
+
+  if (debug_visitor_) {
+    const size_t header_list_size =
+        GetUncompressedSerializedLength(headers.header_block());
+    debug_visitor_->OnSendCompressedFrame(headers.stream_id(),
+                                          SpdyFrameType::HEADERS,
+                                          header_list_size, builder.length());
+  }
+
+  return ok;
+}
+
+bool SpdyFramer::SerializeWindowUpdate(const SpdyWindowUpdateIR& window_update,
+                                       ZeroCopyOutputBuffer* output) const {
+  SpdyFrameBuilder builder(kWindowUpdateFrameSize, output);
+  bool ok = builder.BeginNewFrame(SpdyFrameType::WINDOW_UPDATE, kNoFlags,
+                                  window_update.stream_id());
+  ok = ok && builder.WriteUInt32(window_update.delta());
+  DCHECK_EQ(kWindowUpdateFrameSize, builder.length());
+  return ok;
+}
+
+bool SpdyFramer::SerializePushPromise(const SpdyPushPromiseIR& push_promise,
+                                      ZeroCopyOutputBuffer* output) {
+  uint8_t flags = 0;
+  size_t size = 0;
+  SpdyString hpack_encoding;
+  SerializePushPromiseBuilderHelper(push_promise, &flags, &hpack_encoding,
+                                    &size);
+
+  bool ok = true;
+  SpdyFrameBuilder builder(size, output);
+  size_t length =
+      std::min(size, kHttp2MaxControlFrameSendSize) - kFrameHeaderSize;
+  ok = builder.BeginNewFrame(SpdyFrameType::PUSH_PROMISE, flags,
+                             push_promise.stream_id(), length);
+
+  int padding_payload_len = 0;
+  if (push_promise.padded()) {
+    ok = ok && builder.WriteUInt8(push_promise.padding_payload_len()) &&
+         builder.WriteUInt32(push_promise.promised_stream_id());
+    DCHECK_EQ(kPushPromiseFrameMinimumSize + kPadLengthFieldSize,
+              builder.length());
+
+    padding_payload_len = push_promise.padding_payload_len();
+  } else {
+    ok = ok && builder.WriteUInt32(push_promise.promised_stream_id());
+    DCHECK_EQ(kPushPromiseFrameMinimumSize, builder.length());
+  }
+
+  ok = ok && WritePayloadWithContinuation(
+                 &builder, hpack_encoding, push_promise.stream_id(),
+                 SpdyFrameType::PUSH_PROMISE, padding_payload_len);
+
+  if (debug_visitor_) {
+    const size_t header_list_size =
+        GetUncompressedSerializedLength(push_promise.header_block());
+    debug_visitor_->OnSendCompressedFrame(push_promise.stream_id(),
+                                          SpdyFrameType::PUSH_PROMISE,
+                                          header_list_size, builder.length());
+  }
+
+  return ok;
+}
+
+bool SpdyFramer::SerializeContinuation(const SpdyContinuationIR& continuation,
+                                       ZeroCopyOutputBuffer* output) const {
+  const SpdyString& encoding = continuation.encoding();
+  size_t frame_size = kContinuationFrameMinimumSize + encoding.size();
+  SpdyFrameBuilder builder(frame_size, output);
+  uint8_t flags = continuation.end_headers() ? HEADERS_FLAG_END_HEADERS : 0;
+  bool ok = builder.BeginNewFrame(SpdyFrameType::CONTINUATION, flags,
+                                  continuation.stream_id(),
+                                  frame_size - kFrameHeaderSize);
+  DCHECK_EQ(kFrameHeaderSize, builder.length());
+
+  ok = ok && builder.WriteBytes(encoding.data(), encoding.size());
+  return ok;
+}
+
+bool SpdyFramer::SerializeAltSvc(const SpdyAltSvcIR& altsvc_ir,
+                                 ZeroCopyOutputBuffer* output) {
+  SpdyString value;
+  size_t size = 0;
+  SerializeAltSvcBuilderHelper(altsvc_ir, &value, &size);
+  SpdyFrameBuilder builder(size, output);
+  bool ok = builder.BeginNewFrame(SpdyFrameType::ALTSVC, kNoFlags,
+                                  altsvc_ir.stream_id()) &&
+            builder.WriteUInt16(altsvc_ir.origin().length()) &&
+            builder.WriteBytes(altsvc_ir.origin().data(),
+                               altsvc_ir.origin().length()) &&
+            builder.WriteBytes(value.data(), value.length());
+  DCHECK_LT(kGetAltSvcFrameMinimumSize, builder.length());
+  return ok;
+}
+
+bool SpdyFramer::SerializePriority(const SpdyPriorityIR& priority,
+                                   ZeroCopyOutputBuffer* output) const {
+  SpdyFrameBuilder builder(kPriorityFrameSize, output);
+  bool ok = builder.BeginNewFrame(SpdyFrameType::PRIORITY, kNoFlags,
+                                  priority.stream_id());
+  ok = ok &&
+       builder.WriteUInt32(PackStreamDependencyValues(
+           priority.exclusive(), priority.parent_stream_id())) &&
+       // Per RFC 7540 section 6.3, serialized weight value is actual value - 1.
+       builder.WriteUInt8(priority.weight() - 1);
+  DCHECK_EQ(kPriorityFrameSize, builder.length());
+  return ok;
+}
+
+bool SpdyFramer::SerializeUnknown(const SpdyUnknownIR& unknown,
+                                  ZeroCopyOutputBuffer* output) const {
+  const size_t total_size = kFrameHeaderSize + unknown.payload().size();
+  SpdyFrameBuilder builder(total_size, output);
+  bool ok = builder.BeginNewUncheckedFrame(
+      unknown.type(), unknown.flags(), unknown.stream_id(), unknown.length());
+  ok = ok &&
+       builder.WriteBytes(unknown.payload().data(), unknown.payload().size());
+  return ok;
+}
+
+namespace {
+
+class FrameSerializationVisitorWithOutput : public SpdyFrameVisitor {
+ public:
+  explicit FrameSerializationVisitorWithOutput(SpdyFramer* framer,
+                                               ZeroCopyOutputBuffer* output)
+      : framer_(framer), output_(output), result_(false) {}
+  ~FrameSerializationVisitorWithOutput() override = default;
+
+  size_t Result() { return result_; }
+
+  void VisitData(const SpdyDataIR& data) override {
+    result_ = framer_->SerializeData(data, output_);
+  }
+  void VisitRstStream(const SpdyRstStreamIR& rst_stream) override {
+    result_ = framer_->SerializeRstStream(rst_stream, output_);
+  }
+  void VisitSettings(const SpdySettingsIR& settings) override {
+    result_ = framer_->SerializeSettings(settings, output_);
+  }
+  void VisitPing(const SpdyPingIR& ping) override {
+    result_ = framer_->SerializePing(ping, output_);
+  }
+  void VisitGoAway(const SpdyGoAwayIR& goaway) override {
+    result_ = framer_->SerializeGoAway(goaway, output_);
+  }
+  void VisitHeaders(const SpdyHeadersIR& headers) override {
+    result_ = framer_->SerializeHeaders(headers, output_);
+  }
+  void VisitWindowUpdate(const SpdyWindowUpdateIR& window_update) override {
+    result_ = framer_->SerializeWindowUpdate(window_update, output_);
+  }
+  void VisitPushPromise(const SpdyPushPromiseIR& push_promise) override {
+    result_ = framer_->SerializePushPromise(push_promise, output_);
+  }
+  void VisitContinuation(const SpdyContinuationIR& continuation) override {
+    result_ = framer_->SerializeContinuation(continuation, output_);
+  }
+  void VisitAltSvc(const SpdyAltSvcIR& altsvc) override {
+    result_ = framer_->SerializeAltSvc(altsvc, output_);
+  }
+  void VisitPriority(const SpdyPriorityIR& priority) override {
+    result_ = framer_->SerializePriority(priority, output_);
+  }
+  void VisitUnknown(const SpdyUnknownIR& unknown) override {
+    result_ = framer_->SerializeUnknown(unknown, output_);
+  }
+
+ private:
+  SpdyFramer* framer_;
+  ZeroCopyOutputBuffer* output_;
+  bool result_;
+};
+
+}  // namespace
+
+size_t SpdyFramer::SerializeFrame(const SpdyFrameIR& frame,
+                                  ZeroCopyOutputBuffer* output) {
+  FrameSerializationVisitorWithOutput visitor(this, output);
+  size_t free_bytes_before = output->BytesFree();
+  frame.Visit(&visitor);
+  return visitor.Result() ? free_bytes_before - output->BytesFree() : 0;
+}
+
+HpackEncoder* SpdyFramer::GetHpackEncoder() {
+  if (hpack_encoder_ == nullptr) {
+    hpack_encoder_ = SpdyMakeUnique<HpackEncoder>(ObtainHpackHuffmanTable());
+    if (!compression_enabled()) {
+      hpack_encoder_->DisableCompression();
+    }
+  }
+  return hpack_encoder_.get();
+}
+
+void SpdyFramer::UpdateHeaderEncoderTableSize(uint32_t value) {
+  GetHpackEncoder()->ApplyHeaderTableSizeSetting(value);
+}
+
+size_t SpdyFramer::header_encoder_table_size() const {
+  if (hpack_encoder_ == nullptr) {
+    return kDefaultHeaderTableSizeSetting;
+  } else {
+    return hpack_encoder_->CurrentHeaderTableSizeSetting();
+  }
+}
+
+void SpdyFramer::SetEncoderHeaderTableDebugVisitor(
+    std::unique_ptr<HpackHeaderTable::DebugVisitorInterface> visitor) {
+  GetHpackEncoder()->SetHeaderTableDebugVisitor(std::move(visitor));
+}
+
+size_t SpdyFramer::EstimateMemoryUsage() const {
+  return SpdyEstimateMemoryUsage(hpack_encoder_);
+}
+
+}  // namespace spdy
diff --git a/spdy/core/spdy_framer.h b/spdy/core/spdy_framer.h
new file mode 100644
index 0000000..e268994
--- /dev/null
+++ b/spdy/core/spdy_framer.h
@@ -0,0 +1,365 @@
+// Copyright (c) 2012 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef QUICHE_SPDY_CORE_SPDY_FRAMER_H_
+#define QUICHE_SPDY_CORE_SPDY_FRAMER_H_
+
+#include <stddef.h>
+
+#include <cstdint>
+#include <map>
+#include <memory>
+#include <utility>
+
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_encoder.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_alt_svc_wire_format.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_header_block.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_headers_handler_interface.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_protocol.h"
+#include "net/third_party/quiche/src/spdy/core/zero_copy_output_buffer.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_export.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string_piece.h"
+
+namespace spdy {
+
+namespace test {
+
+class SpdyFramerPeer;
+class SpdyFramerTest_MultipleContinuationFramesWithIterator_Test;
+class SpdyFramerTest_PushPromiseFramesWithIterator_Test;
+
+}  // namespace test
+
+class SPDY_EXPORT_PRIVATE SpdyFrameSequence {
+ public:
+  virtual ~SpdyFrameSequence() {}
+
+  // Serializes the next frame in the sequence to |output|. Returns the number
+  // of bytes written to |output|.
+  virtual size_t NextFrame(ZeroCopyOutputBuffer* output) = 0;
+
+  // Returns true iff there is at least one more frame in the sequence.
+  virtual bool HasNextFrame() const = 0;
+
+  // Get SpdyFrameIR of the frame to be serialized.
+  virtual const SpdyFrameIR& GetIR() const = 0;
+};
+
+class SPDY_EXPORT_PRIVATE SpdyFramer {
+ public:
+  enum CompressionOption {
+    ENABLE_COMPRESSION,
+    DISABLE_COMPRESSION,
+  };
+
+  // Create a SpdyFrameSequence to serialize |frame_ir|.
+  static std::unique_ptr<SpdyFrameSequence> CreateIterator(
+      SpdyFramer* framer,
+      std::unique_ptr<const SpdyFrameIR> frame_ir);
+
+  // Gets the serialized flags for the given |frame|.
+  static uint8_t GetSerializedFlags(const SpdyFrameIR& frame);
+
+  // Serialize a data frame.
+  static SpdySerializedFrame SerializeData(const SpdyDataIR& data_ir);
+  // Serializes the data frame header and optionally padding length fields,
+  // excluding actual data payload and padding.
+  static SpdySerializedFrame SerializeDataFrameHeaderWithPaddingLengthField(
+      const SpdyDataIR& data_ir);
+
+  // Serializes a WINDOW_UPDATE frame. The WINDOW_UPDATE
+  // frame is used to implement per stream flow control.
+  static SpdySerializedFrame SerializeWindowUpdate(
+      const SpdyWindowUpdateIR& window_update);
+
+  explicit SpdyFramer(CompressionOption option);
+
+  virtual ~SpdyFramer();
+
+  // Set debug callbacks to be called from the framer. The debug visitor is
+  // completely optional and need not be set in order for normal operation.
+  // If this is called multiple times, only the last visitor will be used.
+  void set_debug_visitor(SpdyFramerDebugVisitorInterface* debug_visitor);
+
+  SpdySerializedFrame SerializeRstStream(
+      const SpdyRstStreamIR& rst_stream) const;
+
+  // Serializes a SETTINGS frame. The SETTINGS frame is
+  // used to communicate name/value pairs relevant to the communication channel.
+  SpdySerializedFrame SerializeSettings(const SpdySettingsIR& settings) const;
+
+  // Serializes a PING frame. The unique_id is used to
+  // identify the ping request/response.
+  SpdySerializedFrame SerializePing(const SpdyPingIR& ping) const;
+
+  // Serializes a GOAWAY frame. The GOAWAY frame is used
+  // prior to the shutting down of the TCP connection, and includes the
+  // stream_id of the last stream the sender of the frame is willing to process
+  // to completion.
+  SpdySerializedFrame SerializeGoAway(const SpdyGoAwayIR& goaway) const;
+
+  // Serializes a HEADERS frame. The HEADERS frame is used
+  // for sending headers.
+  SpdySerializedFrame SerializeHeaders(const SpdyHeadersIR& headers);
+
+  // Serializes a PUSH_PROMISE frame. The PUSH_PROMISE frame is used
+  // to inform the client that it will be receiving an additional stream
+  // in response to the original request. The frame includes synthesized
+  // headers to explain the upcoming data.
+  SpdySerializedFrame SerializePushPromise(
+      const SpdyPushPromiseIR& push_promise);
+
+  // Serializes a CONTINUATION frame. The CONTINUATION frame is used
+  // to continue a sequence of header block fragments.
+  SpdySerializedFrame SerializeContinuation(
+      const SpdyContinuationIR& continuation) const;
+
+  // Serializes an ALTSVC frame. The ALTSVC frame advertises the
+  // availability of an alternative service to the client.
+  SpdySerializedFrame SerializeAltSvc(const SpdyAltSvcIR& altsvc);
+
+  // Serializes a PRIORITY frame. The PRIORITY frame advises a change in
+  // the relative priority of the given stream.
+  SpdySerializedFrame SerializePriority(const SpdyPriorityIR& priority) const;
+
+  // Serializes an unknown frame given a frame header and payload.
+  SpdySerializedFrame SerializeUnknown(const SpdyUnknownIR& unknown) const;
+
+  // Serialize a frame of unknown type.
+  SpdySerializedFrame SerializeFrame(const SpdyFrameIR& frame);
+
+  // Serialize a data frame.
+  bool SerializeData(const SpdyDataIR& data,
+                     ZeroCopyOutputBuffer* output) const;
+
+  // Serializes the data frame header and optionally padding length fields,
+  // excluding actual data payload and padding.
+  bool SerializeDataFrameHeaderWithPaddingLengthField(
+      const SpdyDataIR& data,
+      ZeroCopyOutputBuffer* output) const;
+
+  bool SerializeRstStream(const SpdyRstStreamIR& rst_stream,
+                          ZeroCopyOutputBuffer* output) const;
+
+  // Serializes a SETTINGS frame. The SETTINGS frame is
+  // used to communicate name/value pairs relevant to the communication channel.
+  bool SerializeSettings(const SpdySettingsIR& settings,
+                         ZeroCopyOutputBuffer* output) const;
+
+  // Serializes a PING frame. The unique_id is used to
+  // identify the ping request/response.
+  bool SerializePing(const SpdyPingIR& ping,
+                     ZeroCopyOutputBuffer* output) const;
+
+  // Serializes a GOAWAY frame. The GOAWAY frame is used
+  // prior to the shutting down of the TCP connection, and includes the
+  // stream_id of the last stream the sender of the frame is willing to process
+  // to completion.
+  bool SerializeGoAway(const SpdyGoAwayIR& goaway,
+                       ZeroCopyOutputBuffer* output) const;
+
+  // Serializes a HEADERS frame. The HEADERS frame is used
+  // for sending headers.
+  bool SerializeHeaders(const SpdyHeadersIR& headers,
+                        ZeroCopyOutputBuffer* output);
+
+  // Serializes a WINDOW_UPDATE frame. The WINDOW_UPDATE
+  // frame is used to implement per stream flow control.
+  bool SerializeWindowUpdate(const SpdyWindowUpdateIR& window_update,
+                             ZeroCopyOutputBuffer* output) const;
+
+  // Serializes a PUSH_PROMISE frame. The PUSH_PROMISE frame is used
+  // to inform the client that it will be receiving an additional stream
+  // in response to the original request. The frame includes synthesized
+  // headers to explain the upcoming data.
+  bool SerializePushPromise(const SpdyPushPromiseIR& push_promise,
+                            ZeroCopyOutputBuffer* output);
+
+  // Serializes a CONTINUATION frame. The CONTINUATION frame is used
+  // to continue a sequence of header block fragments.
+  bool SerializeContinuation(const SpdyContinuationIR& continuation,
+                             ZeroCopyOutputBuffer* output) const;
+
+  // Serializes an ALTSVC frame. The ALTSVC frame advertises the
+  // availability of an alternative service to the client.
+  bool SerializeAltSvc(const SpdyAltSvcIR& altsvc,
+                       ZeroCopyOutputBuffer* output);
+
+  // Serializes a PRIORITY frame. The PRIORITY frame advises a change in
+  // the relative priority of the given stream.
+  bool SerializePriority(const SpdyPriorityIR& priority,
+                         ZeroCopyOutputBuffer* output) const;
+
+  // Serializes an unknown frame given a frame header and payload.
+  bool SerializeUnknown(const SpdyUnknownIR& unknown,
+                        ZeroCopyOutputBuffer* output) const;
+
+  // Serialize a frame of unknown type.
+  size_t SerializeFrame(const SpdyFrameIR& frame, ZeroCopyOutputBuffer* output);
+
+  // Returns whether this SpdyFramer will compress header blocks using HPACK.
+  bool compression_enabled() const {
+    return compression_option_ == ENABLE_COMPRESSION;
+  }
+
+  void SetHpackIndexingPolicy(HpackEncoder::IndexingPolicy policy) {
+    GetHpackEncoder()->SetIndexingPolicy(std::move(policy));
+  }
+
+  // Updates the maximum size of the header encoder compression table.
+  void UpdateHeaderEncoderTableSize(uint32_t value);
+
+  // Returns the maximum size of the header encoder compression table.
+  size_t header_encoder_table_size() const;
+
+  void SetEncoderHeaderTableDebugVisitor(
+      std::unique_ptr<HpackHeaderTable::DebugVisitorInterface> visitor);
+
+  // Get (and lazily initialize) the HPACK encoder state.
+  HpackEncoder* GetHpackEncoder();
+
+  // Returns the estimate of dynamically allocated memory in bytes.
+  size_t EstimateMemoryUsage() const;
+
+ protected:
+  friend class test::SpdyFramerPeer;
+  friend class test::SpdyFramerTest_MultipleContinuationFramesWithIterator_Test;
+  friend class test::SpdyFramerTest_PushPromiseFramesWithIterator_Test;
+
+  // Iteratively converts a SpdyFrameIR into an appropriate sequence of Spdy
+  // frames.
+  // Example usage:
+  // std::unique_ptr<SpdyFrameSequence> it = CreateIterator(framer, frame_ir);
+  // while (it->HasNextFrame()) {
+  //   if(it->NextFrame(output) == 0) {
+  //     // Write failed;
+  //   }
+  // }
+  class SPDY_EXPORT_PRIVATE SpdyFrameIterator : public SpdyFrameSequence {
+   public:
+    // Creates an iterator with the provided framer.
+    // Does not take ownership of |framer|.
+    // |framer| must outlive this instance.
+    explicit SpdyFrameIterator(SpdyFramer* framer);
+    ~SpdyFrameIterator() override;
+
+    // Serializes the next frame in the sequence to |output|. Returns the number
+    // of bytes written to |output|.
+    size_t NextFrame(ZeroCopyOutputBuffer* output) override;
+
+    // Returns true iff there is at least one more frame in the sequence.
+    bool HasNextFrame() const override;
+
+    // SpdyFrameIterator is neither copyable nor movable.
+    SpdyFrameIterator(const SpdyFrameIterator&) = delete;
+    SpdyFrameIterator& operator=(const SpdyFrameIterator&) = delete;
+
+   protected:
+    virtual size_t GetFrameSizeSansBlock() const = 0;
+    virtual bool SerializeGivenEncoding(const SpdyString& encoding,
+                                        ZeroCopyOutputBuffer* output) const = 0;
+
+    SpdyFramer* GetFramer() const { return framer_; }
+
+    void SetEncoder(const SpdyFrameWithHeaderBlockIR* ir) {
+      encoder_ =
+          framer_->GetHpackEncoder()->EncodeHeaderSet(ir->header_block());
+    }
+
+    bool has_next_frame() const { return has_next_frame_; }
+
+   private:
+    SpdyFramer* const framer_;
+    std::unique_ptr<HpackEncoder::ProgressiveEncoder> encoder_;
+    bool is_first_frame_;
+    bool has_next_frame_;
+  };
+
+  // Iteratively converts a SpdyHeadersIR (with a possibly huge
+  // SpdyHeaderBlock) into an appropriate sequence of SpdySerializedFrames, and
+  // write to the output.
+  class SPDY_EXPORT_PRIVATE SpdyHeaderFrameIterator : public SpdyFrameIterator {
+   public:
+    // Does not take ownership of |framer|. Take ownership of |headers_ir|.
+    SpdyHeaderFrameIterator(SpdyFramer* framer,
+                            std::unique_ptr<const SpdyHeadersIR> headers_ir);
+
+    ~SpdyHeaderFrameIterator() override;
+
+   private:
+    const SpdyFrameIR& GetIR() const override;
+    size_t GetFrameSizeSansBlock() const override;
+    bool SerializeGivenEncoding(const SpdyString& encoding,
+                                ZeroCopyOutputBuffer* output) const override;
+
+    const std::unique_ptr<const SpdyHeadersIR> headers_ir_;
+  };
+
+  // Iteratively converts a SpdyPushPromiseIR (with a possibly huge
+  // SpdyHeaderBlock) into an appropriate sequence of SpdySerializedFrames, and
+  // write to the output.
+  class SPDY_EXPORT_PRIVATE SpdyPushPromiseFrameIterator
+      : public SpdyFrameIterator {
+   public:
+    // Does not take ownership of |framer|. Take ownership of |push_promise_ir|.
+    SpdyPushPromiseFrameIterator(
+        SpdyFramer* framer,
+        std::unique_ptr<const SpdyPushPromiseIR> push_promise_ir);
+
+    ~SpdyPushPromiseFrameIterator() override;
+
+   private:
+    const SpdyFrameIR& GetIR() const override;
+    size_t GetFrameSizeSansBlock() const override;
+    bool SerializeGivenEncoding(const SpdyString& encoding,
+                                ZeroCopyOutputBuffer* output) const override;
+
+    const std::unique_ptr<const SpdyPushPromiseIR> push_promise_ir_;
+  };
+
+  // Converts a SpdyFrameIR into one Spdy frame (a sequence of length 1), and
+  // write it to the output.
+  class SPDY_EXPORT_PRIVATE SpdyControlFrameIterator
+      : public SpdyFrameSequence {
+   public:
+    SpdyControlFrameIterator(SpdyFramer* framer,
+                             std::unique_ptr<const SpdyFrameIR> frame_ir);
+    ~SpdyControlFrameIterator() override;
+
+    size_t NextFrame(ZeroCopyOutputBuffer* output) override;
+
+    bool HasNextFrame() const override;
+
+    const SpdyFrameIR& GetIR() const override;
+
+   private:
+    SpdyFramer* const framer_;
+    std::unique_ptr<const SpdyFrameIR> frame_ir_;
+    bool has_next_frame_ = true;
+  };
+
+ private:
+  void SerializeHeadersBuilderHelper(const SpdyHeadersIR& headers,
+                                     uint8_t* flags,
+                                     size_t* size,
+                                     SpdyString* hpack_encoding,
+                                     int* weight,
+                                     size_t* length_field);
+  void SerializePushPromiseBuilderHelper(const SpdyPushPromiseIR& push_promise,
+                                         uint8_t* flags,
+                                         SpdyString* hpack_encoding,
+                                         size_t* size);
+
+  std::unique_ptr<HpackEncoder> hpack_encoder_;
+
+  SpdyFramerDebugVisitorInterface* debug_visitor_;
+
+  // Determines whether HPACK compression is used.
+  const CompressionOption compression_option_;
+};
+
+}  // namespace spdy
+
+#endif  // QUICHE_SPDY_CORE_SPDY_FRAMER_H_
diff --git a/spdy/core/spdy_framer_test.cc b/spdy/core/spdy_framer_test.cc
new file mode 100644
index 0000000..a08d7d7
--- /dev/null
+++ b/spdy/core/spdy_framer_test.cc
@@ -0,0 +1,4833 @@
+// Copyright (c) 2012 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "net/third_party/quiche/src/spdy/core/spdy_framer.h"
+
+#include <stdlib.h>
+
+#include <algorithm>
+#include <cstdint>
+#include <limits>
+#include <tuple>
+#include <vector>
+
+#include "base/logging.h"
+#include "base/macros.h"
+#include "testing/gmock/include/gmock/gmock.h"
+#include "testing/gtest/include/gtest/gtest.h"
+#include "net/third_party/quiche/src/spdy/core/array_output_buffer.h"
+#include "net/third_party/quiche/src/spdy/core/hpack/hpack_constants.h"
+#include "net/third_party/quiche/src/spdy/core/mock_spdy_framer_visitor.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_bitmasks.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_frame_builder.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_frame_reader.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_protocol.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_test_utils.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_arraysize.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_flags.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_ptr_util.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string_utils.h"
+
+using ::http2::Http2DecoderAdapter;
+using ::testing::_;
+
+namespace spdy {
+
+namespace test {
+
+namespace {
+
+const int64_t kSize = 1024 * 1024;
+char output_buffer[kSize] = "";
+
+// frame_list_char is used to hold frames to be compared with output_buffer.
+const int64_t buffer_size = 64 * 1024;
+char frame_list_char[buffer_size] = "";
+}  // namespace
+
+class MockDebugVisitor : public SpdyFramerDebugVisitorInterface {
+ public:
+  MOCK_METHOD4(OnSendCompressedFrame,
+               void(SpdyStreamId stream_id,
+                    SpdyFrameType type,
+                    size_t payload_len,
+                    size_t frame_len));
+
+  MOCK_METHOD3(OnReceiveCompressedFrame,
+               void(SpdyStreamId stream_id,
+                    SpdyFrameType type,
+                    size_t frame_len));
+};
+
+MATCHER_P(IsFrameUnionOf, frame_list, "") {
+  size_t size_verified = 0;
+  for (const auto& frame : *frame_list) {
+    if (arg.size() < size_verified + frame.size()) {
+      LOG(FATAL) << "Incremental header serialization should not lead to a "
+                 << "higher total frame length than non-incremental method.";
+      return false;
+    }
+    if (memcmp(arg.data() + size_verified, frame.data(), frame.size())) {
+      CompareCharArraysWithHexError(
+          "Header serialization methods should be equivalent: ",
+          reinterpret_cast<unsigned char*>(arg.data() + size_verified),
+          frame.size(), reinterpret_cast<unsigned char*>(frame.data()),
+          frame.size());
+      return false;
+    }
+    size_verified += frame.size();
+  }
+  return size_verified == arg.size();
+}
+
+class SpdyFramerPeer {
+ public:
+  // TODO(dahollings): Remove these methods when deprecating non-incremental
+  // header serialization path.
+  static std::unique_ptr<SpdyHeadersIR> CloneSpdyHeadersIR(
+      const SpdyHeadersIR& headers) {
+    auto new_headers = SpdyMakeUnique<SpdyHeadersIR>(
+        headers.stream_id(), headers.header_block().Clone());
+    new_headers->set_fin(headers.fin());
+    new_headers->set_has_priority(headers.has_priority());
+    new_headers->set_weight(headers.weight());
+    new_headers->set_parent_stream_id(headers.parent_stream_id());
+    new_headers->set_exclusive(headers.exclusive());
+    if (headers.padded()) {
+      new_headers->set_padding_len(headers.padding_payload_len() + 1);
+    }
+    return new_headers;
+  }
+
+  static SpdySerializedFrame SerializeHeaders(SpdyFramer* framer,
+                                              const SpdyHeadersIR& headers) {
+    SpdySerializedFrame serialized_headers_old_version(
+        framer->SerializeHeaders(headers));
+    framer->hpack_encoder_.reset(nullptr);
+    auto* saved_debug_visitor = framer->debug_visitor_;
+    framer->debug_visitor_ = nullptr;
+
+    std::vector<SpdySerializedFrame> frame_list;
+    ArrayOutputBuffer frame_list_buffer(frame_list_char, buffer_size);
+    SpdyFramer::SpdyHeaderFrameIterator it(framer, CloneSpdyHeadersIR(headers));
+    while (it.HasNextFrame()) {
+      size_t size_before = frame_list_buffer.Size();
+      EXPECT_GT(it.NextFrame(&frame_list_buffer), 0u);
+      frame_list.emplace_back(
+          SpdySerializedFrame(frame_list_buffer.Begin() + size_before,
+                              frame_list_buffer.Size() - size_before, false));
+    }
+    framer->debug_visitor_ = saved_debug_visitor;
+
+    EXPECT_THAT(serialized_headers_old_version, IsFrameUnionOf(&frame_list));
+    return serialized_headers_old_version;
+  }
+
+  static SpdySerializedFrame SerializeHeaders(SpdyFramer* framer,
+                                              const SpdyHeadersIR& headers,
+                                              ArrayOutputBuffer* output) {
+    if (output == nullptr) {
+      return SerializeHeaders(framer, headers);
+    }
+    output->Reset();
+    EXPECT_TRUE(framer->SerializeHeaders(headers, output));
+    SpdySerializedFrame serialized_headers_old_version(output->Begin(),
+                                                       output->Size(), false);
+    framer->hpack_encoder_.reset(nullptr);
+    auto* saved_debug_visitor = framer->debug_visitor_;
+    framer->debug_visitor_ = nullptr;
+
+    std::vector<SpdySerializedFrame> frame_list;
+    ArrayOutputBuffer frame_list_buffer(frame_list_char, buffer_size);
+    SpdyFramer::SpdyHeaderFrameIterator it(framer, CloneSpdyHeadersIR(headers));
+    while (it.HasNextFrame()) {
+      size_t size_before = frame_list_buffer.Size();
+      EXPECT_GT(it.NextFrame(&frame_list_buffer), 0u);
+      frame_list.emplace_back(
+          SpdySerializedFrame(frame_list_buffer.Begin() + size_before,
+                              frame_list_buffer.Size() - size_before, false));
+    }
+    framer->debug_visitor_ = saved_debug_visitor;
+
+    EXPECT_THAT(serialized_headers_old_version, IsFrameUnionOf(&frame_list));
+    return serialized_headers_old_version;
+  }
+
+  static std::unique_ptr<SpdyPushPromiseIR> CloneSpdyPushPromiseIR(
+      const SpdyPushPromiseIR& push_promise) {
+    auto new_push_promise = SpdyMakeUnique<SpdyPushPromiseIR>(
+        push_promise.stream_id(), push_promise.promised_stream_id(),
+        push_promise.header_block().Clone());
+    new_push_promise->set_fin(push_promise.fin());
+    if (push_promise.padded()) {
+      new_push_promise->set_padding_len(push_promise.padding_payload_len() + 1);
+    }
+    return new_push_promise;
+  }
+
+  static SpdySerializedFrame SerializePushPromise(
+      SpdyFramer* framer,
+      const SpdyPushPromiseIR& push_promise) {
+    SpdySerializedFrame serialized_headers_old_version =
+        framer->SerializePushPromise(push_promise);
+    framer->hpack_encoder_.reset(nullptr);
+    auto* saved_debug_visitor = framer->debug_visitor_;
+    framer->debug_visitor_ = nullptr;
+
+    std::vector<SpdySerializedFrame> frame_list;
+    ArrayOutputBuffer frame_list_buffer(frame_list_char, buffer_size);
+    frame_list_buffer.Reset();
+    SpdyFramer::SpdyPushPromiseFrameIterator it(
+        framer, CloneSpdyPushPromiseIR(push_promise));
+    while (it.HasNextFrame()) {
+      size_t size_before = frame_list_buffer.Size();
+      EXPECT_GT(it.NextFrame(&frame_list_buffer), 0u);
+      frame_list.emplace_back(
+          SpdySerializedFrame(frame_list_buffer.Begin() + size_before,
+                              frame_list_buffer.Size() - size_before, false));
+    }
+    framer->debug_visitor_ = saved_debug_visitor;
+
+    EXPECT_THAT(serialized_headers_old_version, IsFrameUnionOf(&frame_list));
+    return serialized_headers_old_version;
+  }
+
+  static SpdySerializedFrame SerializePushPromise(
+      SpdyFramer* framer,
+      const SpdyPushPromiseIR& push_promise,
+      ArrayOutputBuffer* output) {
+    if (output == nullptr) {
+      return SerializePushPromise(framer, push_promise);
+    }
+    output->Reset();
+    EXPECT_TRUE(framer->SerializePushPromise(push_promise, output));
+    SpdySerializedFrame serialized_headers_old_version(output->Begin(),
+                                                       output->Size(), false);
+    framer->hpack_encoder_.reset(nullptr);
+    auto* saved_debug_visitor = framer->debug_visitor_;
+    framer->debug_visitor_ = nullptr;
+
+    std::vector<SpdySerializedFrame> frame_list;
+    ArrayOutputBuffer frame_list_buffer(frame_list_char, buffer_size);
+    frame_list_buffer.Reset();
+    SpdyFramer::SpdyPushPromiseFrameIterator it(
+        framer, CloneSpdyPushPromiseIR(push_promise));
+    while (it.HasNextFrame()) {
+      size_t size_before = frame_list_buffer.Size();
+      EXPECT_GT(it.NextFrame(&frame_list_buffer), 0u);
+      frame_list.emplace_back(
+          SpdySerializedFrame(frame_list_buffer.Begin() + size_before,
+                              frame_list_buffer.Size() - size_before, false));
+    }
+    framer->debug_visitor_ = saved_debug_visitor;
+
+    EXPECT_THAT(serialized_headers_old_version, IsFrameUnionOf(&frame_list));
+    return serialized_headers_old_version;
+  }
+};
+
+class TestSpdyVisitor : public SpdyFramerVisitorInterface,
+                        public SpdyFramerDebugVisitorInterface {
+ public:
+  // This is larger than our max frame size because header blocks that
+  // are too long can spill over into CONTINUATION frames.
+  static const size_t kDefaultHeaderBufferSize = 16 * 1024 * 1024;
+
+  explicit TestSpdyVisitor(SpdyFramer::CompressionOption option)
+      : framer_(option),
+        error_count_(0),
+        headers_frame_count_(0),
+        push_promise_frame_count_(0),
+        goaway_count_(0),
+        setting_count_(0),
+        settings_ack_sent_(0),
+        settings_ack_received_(0),
+        continuation_count_(0),
+        altsvc_count_(0),
+        priority_count_(0),
+        on_unknown_frame_result_(false),
+        last_window_update_stream_(0),
+        last_window_update_delta_(0),
+        last_push_promise_stream_(0),
+        last_push_promise_promised_stream_(0),
+        data_bytes_(0),
+        fin_frame_count_(0),
+        fin_flag_count_(0),
+        end_of_stream_count_(0),
+        control_frame_header_data_count_(0),
+        zero_length_control_frame_header_data_count_(0),
+        data_frame_count_(0),
+        last_payload_len_(0),
+        last_frame_len_(0),
+        header_buffer_(new char[kDefaultHeaderBufferSize]),
+        header_buffer_length_(0),
+        header_buffer_size_(kDefaultHeaderBufferSize),
+        header_stream_id_(static_cast<SpdyStreamId>(-1)),
+        header_control_type_(SpdyFrameType::DATA),
+        header_buffer_valid_(false) {}
+
+  void OnError(Http2DecoderAdapter::SpdyFramerError error) override {
+    VLOG(1) << "SpdyFramer Error: "
+            << Http2DecoderAdapter::SpdyFramerErrorToString(error);
+    ++error_count_;
+  }
+
+  void OnDataFrameHeader(SpdyStreamId stream_id,
+                         size_t length,
+                         bool fin) override {
+    VLOG(1) << "OnDataFrameHeader(" << stream_id << ", " << length << ", "
+            << fin << ")";
+    ++data_frame_count_;
+    header_stream_id_ = stream_id;
+  }
+
+  void OnStreamFrameData(SpdyStreamId stream_id,
+                         const char* data,
+                         size_t len) override {
+    VLOG(1) << "OnStreamFrameData(" << stream_id << ", data, " << len << ", "
+            << ")   data:\n"
+            << SpdyHexDump(SpdyStringPiece(data, len));
+    EXPECT_EQ(header_stream_id_, stream_id);
+
+    data_bytes_ += len;
+  }
+
+  void OnStreamEnd(SpdyStreamId stream_id) override {
+    VLOG(1) << "OnStreamEnd(" << stream_id << ")";
+    EXPECT_EQ(header_stream_id_, stream_id);
+    ++end_of_stream_count_;
+  }
+
+  void OnStreamPadLength(SpdyStreamId stream_id, size_t value) override {
+    VLOG(1) << "OnStreamPadding(" << stream_id << ", " << value << ")\n";
+    EXPECT_EQ(header_stream_id_, stream_id);
+    // Count the padding length field byte against total data bytes.
+    data_bytes_ += 1;
+  }
+
+  void OnStreamPadding(SpdyStreamId stream_id, size_t len) override {
+    VLOG(1) << "OnStreamPadding(" << stream_id << ", " << len << ")\n";
+    EXPECT_EQ(header_stream_id_, stream_id);
+    data_bytes_ += len;
+  }
+
+  SpdyHeadersHandlerInterface* OnHeaderFrameStart(
+      SpdyStreamId stream_id) override {
+    if (headers_handler_ == nullptr) {
+      headers_handler_ = SpdyMakeUnique<TestHeadersHandler>();
+    }
+    return headers_handler_.get();
+  }
+
+  void OnHeaderFrameEnd(SpdyStreamId stream_id) override {
+    CHECK(headers_handler_ != nullptr);
+    headers_ = headers_handler_->decoded_block().Clone();
+    header_bytes_received_ = headers_handler_->header_bytes_parsed();
+    headers_handler_.reset();
+  }
+
+  void OnRstStream(SpdyStreamId stream_id, SpdyErrorCode error_code) override {
+    VLOG(1) << "OnRstStream(" << stream_id << ", " << error_code << ")";
+    ++fin_frame_count_;
+  }
+
+  void OnSetting(SpdySettingsId id, uint32_t value) override {
+    VLOG(1) << "OnSetting(" << id << ", " << std::hex << value << ")";
+    ++setting_count_;
+  }
+
+  void OnSettingsAck() override {
+    VLOG(1) << "OnSettingsAck";
+    ++settings_ack_received_;
+  }
+
+  void OnSettingsEnd() override {
+    VLOG(1) << "OnSettingsEnd";
+    ++settings_ack_sent_;
+  }
+
+  void OnPing(SpdyPingId unique_id, bool is_ack) override {
+    LOG(DFATAL) << "OnPing(" << unique_id << ", " << (is_ack ? 1 : 0) << ")";
+  }
+
+  void OnGoAway(SpdyStreamId last_accepted_stream_id,
+                SpdyErrorCode error_code) override {
+    VLOG(1) << "OnGoAway(" << last_accepted_stream_id << ", " << error_code
+            << ")";
+    ++goaway_count_;
+  }
+
+  void OnHeaders(SpdyStreamId stream_id,
+                 bool has_priority,
+                 int weight,
+                 SpdyStreamId parent_stream_id,
+                 bool exclusive,
+                 bool fin,
+                 bool end) override {
+    VLOG(1) << "OnHeaders(" << stream_id << ", " << has_priority << ", "
+            << weight << ", " << parent_stream_id << ", " << exclusive << ", "
+            << fin << ", " << end << ")";
+    ++headers_frame_count_;
+    InitHeaderStreaming(SpdyFrameType::HEADERS, stream_id);
+    if (fin) {
+      ++fin_flag_count_;
+    }
+    header_has_priority_ = has_priority;
+    header_parent_stream_id_ = parent_stream_id;
+    header_exclusive_ = exclusive;
+  }
+
+  void OnWindowUpdate(SpdyStreamId stream_id, int delta_window_size) override {
+    VLOG(1) << "OnWindowUpdate(" << stream_id << ", " << delta_window_size
+            << ")";
+    last_window_update_stream_ = stream_id;
+    last_window_update_delta_ = delta_window_size;
+  }
+
+  void OnPushPromise(SpdyStreamId stream_id,
+                     SpdyStreamId promised_stream_id,
+                     bool end) override {
+    VLOG(1) << "OnPushPromise(" << stream_id << ", " << promised_stream_id
+            << ", " << end << ")";
+    ++push_promise_frame_count_;
+    InitHeaderStreaming(SpdyFrameType::PUSH_PROMISE, stream_id);
+    last_push_promise_stream_ = stream_id;
+    last_push_promise_promised_stream_ = promised_stream_id;
+  }
+
+  void OnContinuation(SpdyStreamId stream_id, bool end) override {
+    VLOG(1) << "OnContinuation(" << stream_id << ", " << end << ")";
+    ++continuation_count_;
+  }
+
+  void OnAltSvc(SpdyStreamId stream_id,
+                SpdyStringPiece origin,
+                const SpdyAltSvcWireFormat::AlternativeServiceVector&
+                    altsvc_vector) override {
+    VLOG(1) << "OnAltSvc(" << stream_id << ", \"" << origin
+            << "\", altsvc_vector)";
+    test_altsvc_ir_ = SpdyMakeUnique<SpdyAltSvcIR>(stream_id);
+    if (origin.length() > 0) {
+      test_altsvc_ir_->set_origin(SpdyString(origin));
+    }
+    for (const auto& altsvc : altsvc_vector) {
+      test_altsvc_ir_->add_altsvc(altsvc);
+    }
+    ++altsvc_count_;
+  }
+
+  void OnPriority(SpdyStreamId stream_id,
+                  SpdyStreamId parent_stream_id,
+                  int weight,
+                  bool exclusive) override {
+    VLOG(1) << "OnPriority(" << stream_id << ", " << parent_stream_id << ", "
+            << weight << ", " << (exclusive ? 1 : 0) << ")";
+    ++priority_count_;
+  }
+
+  bool OnUnknownFrame(SpdyStreamId stream_id, uint8_t frame_type) override {
+    VLOG(1) << "OnUnknownFrame(" << stream_id << ", " << frame_type << ")";
+    return on_unknown_frame_result_;
+  }
+
+  void OnSendCompressedFrame(SpdyStreamId stream_id,
+                             SpdyFrameType type,
+                             size_t payload_len,
+                             size_t frame_len) override {
+    VLOG(1) << "OnSendCompressedFrame(" << stream_id << ", " << type << ", "
+            << payload_len << ", " << frame_len << ")";
+    last_payload_len_ = payload_len;
+    last_frame_len_ = frame_len;
+  }
+
+  void OnReceiveCompressedFrame(SpdyStreamId stream_id,
+                                SpdyFrameType type,
+                                size_t frame_len) override {
+    VLOG(1) << "OnReceiveCompressedFrame(" << stream_id << ", " << type << ", "
+            << frame_len << ")";
+    last_frame_len_ = frame_len;
+  }
+
+  // Convenience function which runs a framer simulation with particular input.
+  void SimulateInFramer(const unsigned char* input, size_t size) {
+    deframer_.set_visitor(this);
+    size_t input_remaining = size;
+    const char* input_ptr = reinterpret_cast<const char*>(input);
+    while (input_remaining > 0 && deframer_.spdy_framer_error() ==
+                                      Http2DecoderAdapter::SPDY_NO_ERROR) {
+      // To make the tests more interesting, we feed random (and small) chunks
+      // into the framer.  This simulates getting strange-sized reads from
+      // the socket.
+      const size_t kMaxReadSize = 32;
+      size_t bytes_read =
+          (rand() % std::min(input_remaining, kMaxReadSize)) + 1;
+      size_t bytes_processed = deframer_.ProcessInput(input_ptr, bytes_read);
+      input_remaining -= bytes_processed;
+      input_ptr += bytes_processed;
+    }
+  }
+
+  void InitHeaderStreaming(SpdyFrameType header_control_type,
+                           SpdyStreamId stream_id) {
+    if (!IsDefinedFrameType(SerializeFrameType(header_control_type))) {
+      DLOG(FATAL) << "Attempted to init header streaming with "
+                  << "invalid control frame type: " << header_control_type;
+    }
+    memset(header_buffer_.get(), 0, header_buffer_size_);
+    header_buffer_length_ = 0;
+    header_stream_id_ = stream_id;
+    header_control_type_ = header_control_type;
+    header_buffer_valid_ = true;
+  }
+
+  void set_extension_visitor(ExtensionVisitorInterface* extension) {
+    deframer_.set_extension_visitor(extension);
+  }
+
+  // Override the default buffer size (16K). Call before using the framer!
+  void set_header_buffer_size(size_t header_buffer_size) {
+    header_buffer_size_ = header_buffer_size;
+    header_buffer_.reset(new char[header_buffer_size]);
+  }
+
+  SpdyFramer framer_;
+  Http2DecoderAdapter deframer_;
+
+  // Counters from the visitor callbacks.
+  int error_count_;
+  int headers_frame_count_;
+  int push_promise_frame_count_;
+  int goaway_count_;
+  int setting_count_;
+  int settings_ack_sent_;
+  int settings_ack_received_;
+  int continuation_count_;
+  int altsvc_count_;
+  int priority_count_;
+  std::unique_ptr<SpdyAltSvcIR> test_altsvc_ir_;
+  bool on_unknown_frame_result_;
+  SpdyStreamId last_window_update_stream_;
+  int last_window_update_delta_;
+  SpdyStreamId last_push_promise_stream_;
+  SpdyStreamId last_push_promise_promised_stream_;
+  int data_bytes_;
+  int fin_frame_count_;      // The count of RST_STREAM type frames received.
+  int fin_flag_count_;       // The count of frames with the FIN flag set.
+  int end_of_stream_count_;  // The count of zero-length data frames.
+  int control_frame_header_data_count_;  // The count of chunks received.
+  // The count of zero-length control frame header data chunks received.
+  int zero_length_control_frame_header_data_count_;
+  int data_frame_count_;
+  size_t last_payload_len_;
+  size_t last_frame_len_;
+
+  // Header block streaming state:
+  std::unique_ptr<char[]> header_buffer_;
+  size_t header_buffer_length_;
+  size_t header_buffer_size_;
+  size_t header_bytes_received_;
+  SpdyStreamId header_stream_id_;
+  SpdyFrameType header_control_type_;
+  bool header_buffer_valid_;
+  std::unique_ptr<TestHeadersHandler> headers_handler_;
+  SpdyHeaderBlock headers_;
+  bool header_has_priority_;
+  SpdyStreamId header_parent_stream_id_;
+  bool header_exclusive_;
+};
+
+class TestExtension : public ExtensionVisitorInterface {
+ public:
+  void OnSetting(SpdySettingsId id, uint32_t value) override {
+    settings_received_.push_back({id, value});
+  }
+
+  // Called when non-standard frames are received.
+  bool OnFrameHeader(SpdyStreamId stream_id,
+                     size_t length,
+                     uint8_t type,
+                     uint8_t flags) override {
+    stream_id_ = stream_id;
+    length_ = length;
+    type_ = type;
+    flags_ = flags;
+    return true;
+  }
+
+  // The payload for a single frame may be delivered as multiple calls to
+  // OnFramePayload.
+  void OnFramePayload(const char* data, size_t len) override {
+    payload_.append(data, len);
+  }
+
+  std::vector<std::pair<SpdySettingsId, uint32_t>> settings_received_;
+  SpdyStreamId stream_id_ = 0;
+  size_t length_ = 0;
+  uint8_t type_ = 0;
+  uint8_t flags_ = 0;
+  SpdyString payload_;
+};
+
+// Exposes SpdyUnknownIR::set_length() for testing purposes.
+class TestSpdyUnknownIR : public SpdyUnknownIR {
+ public:
+  using SpdyUnknownIR::set_length;
+  using SpdyUnknownIR::SpdyUnknownIR;
+};
+
+enum Output { USE, NOT_USE };
+
+class SpdyFramerTest : public ::testing::TestWithParam<Output> {
+ public:
+  SpdyFramerTest()
+      : output_(output_buffer, kSize),
+        framer_(SpdyFramer::ENABLE_COMPRESSION) {}
+
+ protected:
+  void SetUp() override {
+    switch (GetParam()) {
+      case USE:
+        use_output_ = true;
+        break;
+      case NOT_USE:
+        // TODO(yasong): remove this case after
+        // gfe2_reloadable_flag_write_queue_zero_copy_buffer deprecates.
+        use_output_ = false;
+        break;
+    }
+  }
+
+  void CompareFrame(const SpdyString& description,
+                    const SpdySerializedFrame& actual_frame,
+                    const unsigned char* expected,
+                    const int expected_len) {
+    const unsigned char* actual =
+        reinterpret_cast<const unsigned char*>(actual_frame.data());
+    CompareCharArraysWithHexError(description, actual, actual_frame.size(),
+                                  expected, expected_len);
+  }
+
+  bool use_output_ = false;
+  ArrayOutputBuffer output_;
+  SpdyFramer framer_;
+  Http2DecoderAdapter deframer_;
+};
+
+INSTANTIATE_TEST_CASE_P(SpdyFramerTests,
+                        SpdyFramerTest,
+                        ::testing::Values(USE, NOT_USE));
+
+// Test that we can encode and decode a SpdyHeaderBlock in serialized form.
+TEST_P(SpdyFramerTest, HeaderBlockInBuffer) {
+  SpdyFramer framer(SpdyFramer::DISABLE_COMPRESSION);
+
+  // Encode the header block into a Headers frame.
+  SpdyHeadersIR headers(/* stream_id = */ 1);
+  headers.SetHeader("alpha", "beta");
+  headers.SetHeader("gamma", "charlie");
+  headers.SetHeader("cookie", "key1=value1; key2=value2");
+  SpdySerializedFrame frame(
+      SpdyFramerPeer::SerializeHeaders(&framer, headers, &output_));
+
+  TestSpdyVisitor visitor(SpdyFramer::DISABLE_COMPRESSION);
+  visitor.SimulateInFramer(reinterpret_cast<unsigned char*>(frame.data()),
+                           frame.size());
+
+  EXPECT_EQ(0, visitor.zero_length_control_frame_header_data_count_);
+  EXPECT_EQ(headers.header_block(), visitor.headers_);
+}
+
+// Test that if there's not a full frame, we fail to parse it.
+TEST_P(SpdyFramerTest, UndersizedHeaderBlockInBuffer) {
+  SpdyFramer framer(SpdyFramer::DISABLE_COMPRESSION);
+
+  // Encode the header block into a Headers frame.
+  SpdyHeadersIR headers(/* stream_id = */ 1);
+  headers.SetHeader("alpha", "beta");
+  headers.SetHeader("gamma", "charlie");
+  SpdySerializedFrame frame(
+      SpdyFramerPeer::SerializeHeaders(&framer, headers, &output_));
+
+  TestSpdyVisitor visitor(SpdyFramer::DISABLE_COMPRESSION);
+  visitor.SimulateInFramer(reinterpret_cast<unsigned char*>(frame.data()),
+                           frame.size() - 2);
+
+  EXPECT_EQ(0, visitor.zero_length_control_frame_header_data_count_);
+  EXPECT_THAT(visitor.headers_, testing::IsEmpty());
+}
+
+// Test that we can encode and decode stream dependency values in a header
+// frame.
+TEST_P(SpdyFramerTest, HeaderStreamDependencyValues) {
+  SpdyFramer framer(SpdyFramer::DISABLE_COMPRESSION);
+
+  const SpdyStreamId parent_stream_id_test_array[] = {0, 3};
+  for (SpdyStreamId parent_stream_id : parent_stream_id_test_array) {
+    const bool exclusive_test_array[] = {true, false};
+    for (bool exclusive : exclusive_test_array) {
+      SpdyHeadersIR headers(1);
+      headers.set_has_priority(true);
+      headers.set_parent_stream_id(parent_stream_id);
+      headers.set_exclusive(exclusive);
+      SpdySerializedFrame frame(
+          SpdyFramerPeer::SerializeHeaders(&framer, headers, &output_));
+
+      TestSpdyVisitor visitor(SpdyFramer::DISABLE_COMPRESSION);
+      visitor.SimulateInFramer(reinterpret_cast<unsigned char*>(frame.data()),
+                               frame.size());
+
+      EXPECT_TRUE(visitor.header_has_priority_);
+      EXPECT_EQ(parent_stream_id, visitor.header_parent_stream_id_);
+      EXPECT_EQ(exclusive, visitor.header_exclusive_);
+    }
+  }
+}
+
+// Test that if we receive a frame with payload length field at the
+// advertised max size, we do not set an error in ProcessInput.
+TEST_P(SpdyFramerTest, AcceptMaxFrameSizeSetting) {
+  testing::StrictMock<test::MockSpdyFramerVisitor> visitor;
+  deframer_.set_visitor(&visitor);
+
+  // DATA frame with maximum allowed payload length.
+  unsigned char kH2FrameData[] = {
+      0x00, 0x40, 0x00,        // Length: 2^14
+      0x00,                    //   Type: HEADERS
+      0x00,                    //  Flags: None
+      0x00, 0x00, 0x00, 0x01,  // Stream: 1
+      0x00, 0x00, 0x00, 0x00,  // Junk payload
+  };
+
+  SpdySerializedFrame frame(reinterpret_cast<char*>(kH2FrameData),
+                            sizeof(kH2FrameData), false);
+
+  EXPECT_CALL(visitor, OnDataFrameHeader(1, 1 << 14, false));
+  EXPECT_CALL(visitor, OnStreamFrameData(1, _, 4));
+  deframer_.ProcessInput(frame.data(), frame.size());
+  EXPECT_FALSE(deframer_.HasError());
+}
+
+// Test that if we receive a frame with payload length larger than the
+// advertised max size, we set an error of SPDY_INVALID_CONTROL_FRAME_SIZE.
+TEST_P(SpdyFramerTest, ExceedMaxFrameSizeSetting) {
+  testing::StrictMock<test::MockSpdyFramerVisitor> visitor;
+  deframer_.set_visitor(&visitor);
+
+  // DATA frame with too large payload length.
+  unsigned char kH2FrameData[] = {
+      0x00, 0x40, 0x01,        // Length: 2^14 + 1
+      0x00,                    //   Type: HEADERS
+      0x00,                    //  Flags: None
+      0x00, 0x00, 0x00, 0x01,  // Stream: 1
+      0x00, 0x00, 0x00, 0x00,  // Junk payload
+  };
+
+  SpdySerializedFrame frame(reinterpret_cast<char*>(kH2FrameData),
+                            sizeof(kH2FrameData), false);
+
+  EXPECT_CALL(visitor, OnError(Http2DecoderAdapter::SPDY_OVERSIZED_PAYLOAD));
+  deframer_.ProcessInput(frame.data(), frame.size());
+  EXPECT_TRUE(deframer_.HasError());
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_OVERSIZED_PAYLOAD,
+            deframer_.spdy_framer_error())
+      << Http2DecoderAdapter::SpdyFramerErrorToString(
+             deframer_.spdy_framer_error());
+}
+
+// Test that if we receive a DATA frame with padding length larger than the
+// payload length, we set an error of SPDY_INVALID_PADDING
+TEST_P(SpdyFramerTest, OversizedDataPaddingError) {
+  testing::StrictMock<test::MockSpdyFramerVisitor> visitor;
+  deframer_.set_visitor(&visitor);
+
+  // DATA frame with invalid padding length.
+  // |kH2FrameData| has to be |unsigned char|, because Chromium on Windows uses
+  // MSVC, where |char| is signed by default, which would not compile because of
+  // the element exceeding 127.
+  unsigned char kH2FrameData[] = {
+      0x00, 0x00, 0x05,        // Length: 5
+      0x00,                    //   Type: DATA
+      0x09,                    //  Flags: END_STREAM|PADDED
+      0x00, 0x00, 0x00, 0x01,  // Stream: 1
+      0xff,                    // PadLen: 255 trailing bytes (Too Long)
+      0x00, 0x00, 0x00, 0x00,  // Padding
+  };
+
+  SpdySerializedFrame frame(reinterpret_cast<char*>(kH2FrameData),
+                            sizeof(kH2FrameData), false);
+
+  {
+    testing::InSequence seq;
+    EXPECT_CALL(visitor, OnDataFrameHeader(1, 5, 1));
+    EXPECT_CALL(visitor, OnStreamPadding(1, 1));
+    EXPECT_CALL(visitor, OnError(Http2DecoderAdapter::SPDY_INVALID_PADDING));
+  }
+  EXPECT_GT(frame.size(), deframer_.ProcessInput(frame.data(), frame.size()));
+  EXPECT_TRUE(deframer_.HasError());
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_INVALID_PADDING,
+            deframer_.spdy_framer_error())
+      << Http2DecoderAdapter::SpdyFramerErrorToString(
+             deframer_.spdy_framer_error());
+}
+
+// Test that if we receive a DATA frame with padding length not larger than the
+// payload length, we do not set an error of SPDY_INVALID_PADDING
+TEST_P(SpdyFramerTest, CorrectlySizedDataPaddingNoError) {
+  testing::StrictMock<test::MockSpdyFramerVisitor> visitor;
+
+  deframer_.set_visitor(&visitor);
+
+  // DATA frame with valid Padding length
+  char kH2FrameData[] = {
+      0x00, 0x00, 0x05,        // Length: 5
+      0x00,                    //   Type: DATA
+      0x08,                    //  Flags: PADDED
+      0x00, 0x00, 0x00, 0x01,  // Stream: 1
+      0x04,                    // PadLen: 4 trailing bytes
+      0x00, 0x00, 0x00, 0x00,  // Padding
+  };
+
+  SpdySerializedFrame frame(kH2FrameData, sizeof(kH2FrameData), false);
+
+  {
+    testing::InSequence seq;
+    EXPECT_CALL(visitor, OnDataFrameHeader(1, 5, false));
+    EXPECT_CALL(visitor, OnStreamPadLength(1, 4));
+    EXPECT_CALL(visitor, OnError(_)).Times(0);
+    // Note that OnStreamFrameData(1, _, 1)) is never called
+    // since there is no data, only padding
+    EXPECT_CALL(visitor, OnStreamPadding(1, 4));
+  }
+
+  EXPECT_EQ(frame.size(), deframer_.ProcessInput(frame.data(), frame.size()));
+  EXPECT_FALSE(deframer_.HasError());
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_NO_ERROR, deframer_.spdy_framer_error())
+      << Http2DecoderAdapter::SpdyFramerErrorToString(
+             deframer_.spdy_framer_error());
+}
+
+// Test that if we receive a HEADERS frame with padding length larger than the
+// payload length, we set an error of SPDY_INVALID_PADDING
+TEST_P(SpdyFramerTest, OversizedHeadersPaddingError) {
+  testing::StrictMock<test::MockSpdyFramerVisitor> visitor;
+
+  deframer_.set_visitor(&visitor);
+
+  // HEADERS frame with invalid padding length.
+  // |kH2FrameData| has to be |unsigned char|, because Chromium on Windows uses
+  // MSVC, where |char| is signed by default, which would not compile because of
+  // the element exceeding 127.
+  unsigned char kH2FrameData[] = {
+      0x00, 0x00, 0x05,        // Length: 5
+      0x01,                    //   Type: HEADERS
+      0x08,                    //  Flags: PADDED
+      0x00, 0x00, 0x00, 0x01,  // Stream: 1
+      0xff,                    // PadLen: 255 trailing bytes (Too Long)
+      0x00, 0x00, 0x00, 0x00,  // Padding
+  };
+
+  SpdySerializedFrame frame(reinterpret_cast<char*>(kH2FrameData),
+                            sizeof(kH2FrameData), false);
+
+  EXPECT_CALL(visitor, OnHeaders(1, false, 0, 0, false, false, false));
+  EXPECT_CALL(visitor, OnHeaderFrameStart(1)).Times(1);
+  EXPECT_CALL(visitor, OnError(Http2DecoderAdapter::SPDY_INVALID_PADDING));
+  EXPECT_EQ(frame.size(), deframer_.ProcessInput(frame.data(), frame.size()));
+  EXPECT_TRUE(deframer_.HasError());
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_INVALID_PADDING,
+            deframer_.spdy_framer_error())
+      << Http2DecoderAdapter::SpdyFramerErrorToString(
+             deframer_.spdy_framer_error());
+}
+
+// Test that if we receive a HEADERS frame with padding length not larger
+// than the payload length, we do not set an error of SPDY_INVALID_PADDING
+TEST_P(SpdyFramerTest, CorrectlySizedHeadersPaddingNoError) {
+  testing::StrictMock<test::MockSpdyFramerVisitor> visitor;
+
+  deframer_.set_visitor(&visitor);
+
+  // HEADERS frame with invalid Padding length
+  char kH2FrameData[] = {
+      0x00, 0x00, 0x05,        // Length: 5
+      0x01,                    //   Type: HEADERS
+      0x08,                    //  Flags: PADDED
+      0x00, 0x00, 0x00, 0x01,  // Stream: 1
+      0x04,                    // PadLen: 4 trailing bytes
+      0x00, 0x00, 0x00, 0x00,  // Padding
+  };
+
+  SpdySerializedFrame frame(kH2FrameData, sizeof(kH2FrameData), false);
+
+  EXPECT_CALL(visitor, OnHeaders(1, false, 0, 0, false, false, false));
+  EXPECT_CALL(visitor, OnHeaderFrameStart(1)).Times(1);
+
+  EXPECT_EQ(frame.size(), deframer_.ProcessInput(frame.data(), frame.size()));
+  EXPECT_FALSE(deframer_.HasError());
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_NO_ERROR, deframer_.spdy_framer_error())
+      << Http2DecoderAdapter::SpdyFramerErrorToString(
+             deframer_.spdy_framer_error());
+}
+
+// Test that if we receive a DATA with stream ID zero, we signal an error
+// (but don't crash).
+TEST_P(SpdyFramerTest, DataWithStreamIdZero) {
+  testing::StrictMock<test::MockSpdyFramerVisitor> visitor;
+
+  deframer_.set_visitor(&visitor);
+
+  const char bytes[] = "hello";
+  SpdyDataIR data_ir(/* stream_id = */ 0, bytes);
+  SpdySerializedFrame frame(framer_.SerializeData(data_ir));
+
+  // We shouldn't have to read the whole frame before we signal an error.
+  EXPECT_CALL(visitor, OnError(Http2DecoderAdapter::SPDY_INVALID_STREAM_ID));
+  EXPECT_GT(frame.size(), deframer_.ProcessInput(frame.data(), frame.size()));
+  EXPECT_TRUE(deframer_.HasError());
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_INVALID_STREAM_ID,
+            deframer_.spdy_framer_error())
+      << Http2DecoderAdapter::SpdyFramerErrorToString(
+             deframer_.spdy_framer_error());
+}
+
+// Test that if we receive a HEADERS with stream ID zero, we signal an error
+// (but don't crash).
+TEST_P(SpdyFramerTest, HeadersWithStreamIdZero) {
+  testing::StrictMock<test::MockSpdyFramerVisitor> visitor;
+
+  deframer_.set_visitor(&visitor);
+
+  SpdyHeadersIR headers(/* stream_id = */ 0);
+  headers.SetHeader("alpha", "beta");
+  SpdySerializedFrame frame(
+      SpdyFramerPeer::SerializeHeaders(&framer_, headers, &output_));
+
+  // We shouldn't have to read the whole frame before we signal an error.
+  EXPECT_CALL(visitor, OnError(Http2DecoderAdapter::SPDY_INVALID_STREAM_ID));
+  EXPECT_GT(frame.size(), deframer_.ProcessInput(frame.data(), frame.size()));
+  EXPECT_TRUE(deframer_.HasError());
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_INVALID_STREAM_ID,
+            deframer_.spdy_framer_error())
+      << Http2DecoderAdapter::SpdyFramerErrorToString(
+             deframer_.spdy_framer_error());
+}
+
+// Test that if we receive a PRIORITY with stream ID zero, we signal an error
+// (but don't crash).
+TEST_P(SpdyFramerTest, PriorityWithStreamIdZero) {
+  testing::StrictMock<test::MockSpdyFramerVisitor> visitor;
+
+  deframer_.set_visitor(&visitor);
+
+  SpdyPriorityIR priority_ir(/* stream_id = */ 0,
+                             /* parent_stream_id = */ 1,
+                             /* weight = */ 16,
+                             /* exclusive = */ true);
+  SpdySerializedFrame frame(framer_.SerializeFrame(priority_ir));
+  if (use_output_) {
+    EXPECT_EQ(framer_.SerializeFrame(priority_ir, &output_), frame.size());
+    frame = SpdySerializedFrame(output_.Begin(), output_.Size(), false);
+  }
+
+  // We shouldn't have to read the whole frame before we signal an error.
+  EXPECT_CALL(visitor, OnError(Http2DecoderAdapter::SPDY_INVALID_STREAM_ID));
+  EXPECT_GT(frame.size(), deframer_.ProcessInput(frame.data(), frame.size()));
+  EXPECT_TRUE(deframer_.HasError());
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_INVALID_STREAM_ID,
+            deframer_.spdy_framer_error())
+      << Http2DecoderAdapter::SpdyFramerErrorToString(
+             deframer_.spdy_framer_error());
+}
+
+// Test that if we receive a RST_STREAM with stream ID zero, we signal an error
+// (but don't crash).
+TEST_P(SpdyFramerTest, RstStreamWithStreamIdZero) {
+  testing::StrictMock<test::MockSpdyFramerVisitor> visitor;
+
+  deframer_.set_visitor(&visitor);
+
+  SpdyRstStreamIR rst_stream_ir(/* stream_id = */ 0, ERROR_CODE_PROTOCOL_ERROR);
+  SpdySerializedFrame frame(framer_.SerializeRstStream(rst_stream_ir));
+  if (use_output_) {
+    EXPECT_TRUE(framer_.SerializeRstStream(rst_stream_ir, &output_));
+    frame = SpdySerializedFrame(output_.Begin(), output_.Size(), false);
+  }
+
+  // We shouldn't have to read the whole frame before we signal an error.
+  EXPECT_CALL(visitor, OnError(Http2DecoderAdapter::SPDY_INVALID_STREAM_ID));
+  EXPECT_GT(frame.size(), deframer_.ProcessInput(frame.data(), frame.size()));
+  EXPECT_TRUE(deframer_.HasError());
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_INVALID_STREAM_ID,
+            deframer_.spdy_framer_error())
+      << Http2DecoderAdapter::SpdyFramerErrorToString(
+             deframer_.spdy_framer_error());
+}
+
+// Test that if we receive a SETTINGS with stream ID other than zero,
+// we signal an error (but don't crash).
+TEST_P(SpdyFramerTest, SettingsWithStreamIdNotZero) {
+  testing::StrictMock<test::MockSpdyFramerVisitor> visitor;
+
+  deframer_.set_visitor(&visitor);
+
+  // Settings frame with invalid StreamID of 0x01
+  char kH2FrameData[] = {
+      0x00, 0x00, 0x06,        // Length: 6
+      0x04,                    //   Type: SETTINGS
+      0x00,                    //  Flags: none
+      0x00, 0x00, 0x00, 0x01,  // Stream: 1
+      0x00, 0x04,              //  Param: INITIAL_WINDOW_SIZE
+      0x0a, 0x0b, 0x0c, 0x0d,  //  Value: 168496141
+  };
+
+  SpdySerializedFrame frame(kH2FrameData, sizeof(kH2FrameData), false);
+
+  // We shouldn't have to read the whole frame before we signal an error.
+  EXPECT_CALL(visitor, OnError(Http2DecoderAdapter::SPDY_INVALID_STREAM_ID));
+  EXPECT_GT(frame.size(), deframer_.ProcessInput(frame.data(), frame.size()));
+  EXPECT_TRUE(deframer_.HasError());
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_INVALID_STREAM_ID,
+            deframer_.spdy_framer_error())
+      << Http2DecoderAdapter::SpdyFramerErrorToString(
+             deframer_.spdy_framer_error());
+}
+
+// Test that if we receive a GOAWAY with stream ID other than zero,
+// we signal an error (but don't crash).
+TEST_P(SpdyFramerTest, GoawayWithStreamIdNotZero) {
+  testing::StrictMock<test::MockSpdyFramerVisitor> visitor;
+
+  deframer_.set_visitor(&visitor);
+
+  // GOAWAY frame with invalid StreamID of 0x01
+  char kH2FrameData[] = {
+      0x00, 0x00, 0x0a,        // Length: 10
+      0x07,                    //   Type: GOAWAY
+      0x00,                    //  Flags: none
+      0x00, 0x00, 0x00, 0x01,  // Stream: 1
+      0x00, 0x00, 0x00, 0x00,  //   Last: 0
+      0x00, 0x00, 0x00, 0x00,  //  Error: NO_ERROR
+      0x47, 0x41,              // Description
+  };
+
+  SpdySerializedFrame frame(kH2FrameData, sizeof(kH2FrameData), false);
+
+  // We shouldn't have to read the whole frame before we signal an error.
+  EXPECT_CALL(visitor, OnError(Http2DecoderAdapter::SPDY_INVALID_STREAM_ID));
+  EXPECT_GT(frame.size(), deframer_.ProcessInput(frame.data(), frame.size()));
+  EXPECT_TRUE(deframer_.HasError());
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_INVALID_STREAM_ID,
+            deframer_.spdy_framer_error())
+      << Http2DecoderAdapter::SpdyFramerErrorToString(
+             deframer_.spdy_framer_error());
+}
+
+// Test that if we receive a CONTINUATION with stream ID zero, we signal
+// SPDY_INVALID_STREAM_ID.
+TEST_P(SpdyFramerTest, ContinuationWithStreamIdZero) {
+  testing::StrictMock<test::MockSpdyFramerVisitor> visitor;
+
+  deframer_.set_visitor(&visitor);
+
+  SpdyContinuationIR continuation(/* stream_id = */ 0);
+  auto some_nonsense_encoding =
+      SpdyMakeUnique<SpdyString>("some nonsense encoding");
+  continuation.take_encoding(std::move(some_nonsense_encoding));
+  continuation.set_end_headers(true);
+  SpdySerializedFrame frame(framer_.SerializeContinuation(continuation));
+  if (use_output_) {
+    ASSERT_TRUE(framer_.SerializeContinuation(continuation, &output_));
+    frame = SpdySerializedFrame(output_.Begin(), output_.Size(), false);
+  }
+
+  // We shouldn't have to read the whole frame before we signal an error.
+  EXPECT_CALL(visitor, OnError(Http2DecoderAdapter::SPDY_INVALID_STREAM_ID));
+  EXPECT_GT(frame.size(), deframer_.ProcessInput(frame.data(), frame.size()));
+  EXPECT_TRUE(deframer_.HasError());
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_INVALID_STREAM_ID,
+            deframer_.spdy_framer_error())
+      << Http2DecoderAdapter::SpdyFramerErrorToString(
+             deframer_.spdy_framer_error());
+}
+
+// Test that if we receive a PUSH_PROMISE with stream ID zero, we signal
+// SPDY_INVALID_STREAM_ID.
+TEST_P(SpdyFramerTest, PushPromiseWithStreamIdZero) {
+  testing::StrictMock<test::MockSpdyFramerVisitor> visitor;
+
+  deframer_.set_visitor(&visitor);
+
+  SpdyPushPromiseIR push_promise(/* stream_id = */ 0,
+                                 /* promised_stream_id = */ 4);
+  push_promise.SetHeader("alpha", "beta");
+  SpdySerializedFrame frame(SpdyFramerPeer::SerializePushPromise(
+      &framer_, push_promise, use_output_ ? &output_ : nullptr));
+
+  // We shouldn't have to read the whole frame before we signal an error.
+  EXPECT_CALL(visitor, OnError(Http2DecoderAdapter::SPDY_INVALID_STREAM_ID));
+  EXPECT_GT(frame.size(), deframer_.ProcessInput(frame.data(), frame.size()));
+  EXPECT_TRUE(deframer_.HasError());
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_INVALID_STREAM_ID,
+            deframer_.spdy_framer_error())
+      << Http2DecoderAdapter::SpdyFramerErrorToString(
+             deframer_.spdy_framer_error());
+}
+
+// Test that if we receive a PUSH_PROMISE with promised stream ID zero, we
+// signal SPDY_INVALID_CONTROL_FRAME.
+TEST_P(SpdyFramerTest, PushPromiseWithPromisedStreamIdZero) {
+  testing::StrictMock<test::MockSpdyFramerVisitor> visitor;
+
+  deframer_.set_visitor(&visitor);
+
+  SpdyPushPromiseIR push_promise(/* stream_id = */ 3,
+                                 /* promised_stream_id = */ 0);
+  push_promise.SetHeader("alpha", "beta");
+  SpdySerializedFrame frame(SpdyFramerPeer::SerializePushPromise(
+      &framer_, push_promise, use_output_ ? &output_ : nullptr));
+
+  EXPECT_CALL(visitor,
+              OnError(Http2DecoderAdapter::SPDY_INVALID_CONTROL_FRAME));
+  deframer_.ProcessInput(frame.data(), frame.size());
+  EXPECT_TRUE(deframer_.HasError());
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_INVALID_CONTROL_FRAME,
+            deframer_.spdy_framer_error())
+      << Http2DecoderAdapter::SpdyFramerErrorToString(
+             deframer_.spdy_framer_error());
+}
+
+TEST_P(SpdyFramerTest, MultiValueHeader) {
+  SpdyFramer framer(SpdyFramer::DISABLE_COMPRESSION);
+  SpdyString value("value1\0value2", 13);
+  // TODO(jgraettinger): If this pattern appears again, move to test class.
+  SpdyHeaderBlock header_set;
+  header_set["name"] = value;
+  SpdyString buffer;
+  HpackEncoder encoder(ObtainHpackHuffmanTable());
+  encoder.DisableCompression();
+  encoder.EncodeHeaderSet(header_set, &buffer);
+  // Frame builder with plentiful buffer size.
+  SpdyFrameBuilder frame(1024);
+  frame.BeginNewFrame(SpdyFrameType::HEADERS,
+                      HEADERS_FLAG_PRIORITY | HEADERS_FLAG_END_HEADERS, 3,
+                      buffer.size() + 5 /* priority */);
+  frame.WriteUInt32(0);   // Priority exclusivity and dependent stream.
+  frame.WriteUInt8(255);  // Priority weight.
+  frame.WriteBytes(&buffer[0], buffer.size());
+
+  SpdySerializedFrame control_frame(frame.take());
+
+  TestSpdyVisitor visitor(SpdyFramer::DISABLE_COMPRESSION);
+  visitor.SimulateInFramer(
+      reinterpret_cast<unsigned char*>(control_frame.data()),
+      control_frame.size());
+
+  EXPECT_THAT(visitor.headers_, testing::ElementsAre(testing::Pair(
+                                    "name", SpdyStringPiece(value))));
+}
+
+TEST_P(SpdyFramerTest, CompressEmptyHeaders) {
+  // See https://crbug.com/172383/
+  SpdyHeadersIR headers(1);
+  headers.SetHeader("server", "SpdyServer 1.0");
+  headers.SetHeader("date", "Mon 12 Jan 2009 12:12:12 PST");
+  headers.SetHeader("status", "200");
+  headers.SetHeader("version", "HTTP/1.1");
+  headers.SetHeader("content-type", "text/html");
+  headers.SetHeader("content-length", "12");
+  headers.SetHeader("x-empty-header", "");
+
+  SpdyFramer framer(SpdyFramer::ENABLE_COMPRESSION);
+  SpdySerializedFrame frame1(
+      SpdyFramerPeer::SerializeHeaders(&framer, headers, &output_));
+}
+
+TEST_P(SpdyFramerTest, Basic) {
+  // Send HEADERS frames with PRIORITY and END_HEADERS set.
+  // frame-format off
+  const unsigned char kH2Input[] = {
+      0x00, 0x00, 0x05,        // Length: 5
+      0x01,                    //   Type: HEADERS
+      0x24,                    //  Flags: END_HEADERS|PRIORITY
+      0x00, 0x00, 0x00, 0x01,  // Stream: 1
+      0x00, 0x00, 0x00, 0x00,  // Parent: 0
+      0x82,                    // Weight: 131
+
+      0x00, 0x00, 0x01,        // Length: 1
+      0x01,                    //   Type: HEADERS
+      0x04,                    //  Flags: END_HEADERS
+      0x00, 0x00, 0x00, 0x01,  // Stream: 1
+      0x8c,                    // :status: 200
+
+      0x00, 0x00, 0x0c,        // Length: 12
+      0x00,                    //   Type: DATA
+      0x00,                    //  Flags: none
+      0x00, 0x00, 0x00, 0x01,  // Stream: 1
+      0xde, 0xad, 0xbe, 0xef,  // Payload
+      0xde, 0xad, 0xbe, 0xef,  //
+      0xde, 0xad, 0xbe, 0xef,  //
+
+      0x00, 0x00, 0x05,        // Length: 5
+      0x01,                    //   Type: HEADERS
+      0x24,                    //  Flags: END_HEADERS|PRIORITY
+      0x00, 0x00, 0x00, 0x03,  // Stream: 3
+      0x00, 0x00, 0x00, 0x00,  // Parent: 0
+      0x82,                    // Weight: 131
+
+      0x00, 0x00, 0x08,        // Length: 8
+      0x00,                    //   Type: DATA
+      0x00,                    //  Flags: none
+      0x00, 0x00, 0x00, 0x03,  // Stream: 3
+      0xde, 0xad, 0xbe, 0xef,  // Payload
+      0xde, 0xad, 0xbe, 0xef,  //
+
+      0x00, 0x00, 0x04,        // Length: 4
+      0x00,                    //   Type: DATA
+      0x00,                    //  Flags: none
+      0x00, 0x00, 0x00, 0x01,  // Stream: 1
+      0xde, 0xad, 0xbe, 0xef,  // Payload
+
+      0x00, 0x00, 0x04,        // Length: 4
+      0x03,                    //   Type: RST_STREAM
+      0x00,                    //  Flags: none
+      0x00, 0x00, 0x00, 0x01,  // Stream: 1
+      0x00, 0x00, 0x00, 0x08,  //  Error: CANCEL
+
+      0x00, 0x00, 0x00,        // Length: 0
+      0x00,                    //   Type: DATA
+      0x00,                    //  Flags: none
+      0x00, 0x00, 0x00, 0x03,  // Stream: 3
+
+      0x00, 0x00, 0x04,        // Length: 4
+      0x03,                    //   Type: RST_STREAM
+      0x00,                    //  Flags: none
+      0x00, 0x00, 0x00, 0x03,  // Stream: 3
+      0x00, 0x00, 0x00, 0x08,  //  Error: CANCEL
+  };
+  // frame-format on
+
+  TestSpdyVisitor visitor(SpdyFramer::DISABLE_COMPRESSION);
+  visitor.SimulateInFramer(kH2Input, sizeof(kH2Input));
+
+  EXPECT_EQ(24, visitor.data_bytes_);
+  EXPECT_EQ(0, visitor.error_count_);
+  EXPECT_EQ(2, visitor.fin_frame_count_);
+
+  EXPECT_EQ(3, visitor.headers_frame_count_);
+
+  EXPECT_EQ(0, visitor.fin_flag_count_);
+  EXPECT_EQ(0, visitor.end_of_stream_count_);
+  EXPECT_EQ(4, visitor.data_frame_count_);
+}
+
+// Test that the FIN flag on a data frame signifies EOF.
+TEST_P(SpdyFramerTest, FinOnDataFrame) {
+  // Send HEADERS frames with END_HEADERS set.
+  // frame-format off
+  const unsigned char kH2Input[] = {
+      0x00, 0x00, 0x05,        // Length: 5
+      0x01,                    //   Type: HEADERS
+      0x24,                    //  Flags: END_HEADERS|PRIORITY
+      0x00, 0x00, 0x00, 0x01,  // Stream: 1
+      0x00, 0x00, 0x00, 0x00,  // Parent: 0
+      0x82,                    // Weight: 131
+
+      0x00, 0x00, 0x01,        // Length: 1
+      0x01,                    //   Type: HEADERS
+      0x04,                    //  Flags: END_HEADERS
+      0x00, 0x00, 0x00, 0x01,  // Stream: 1
+      0x8c,                    // :status: 200
+
+      0x00, 0x00, 0x0c,        // Length: 12
+      0x00,                    //   Type: DATA
+      0x00,                    //  Flags: none
+      0x00, 0x00, 0x00, 0x01,  // Stream: 1
+      0xde, 0xad, 0xbe, 0xef,  // Payload
+      0xde, 0xad, 0xbe, 0xef,  //
+      0xde, 0xad, 0xbe, 0xef,  //
+
+      0x00, 0x00, 0x04,        // Length: 4
+      0x00,                    //   Type: DATA
+      0x01,                    //  Flags: END_STREAM
+      0x00, 0x00, 0x00, 0x01,  // Stream: 1
+      0xde, 0xad, 0xbe, 0xef,  // Payload
+  };
+  // frame-format on
+
+  TestSpdyVisitor visitor(SpdyFramer::DISABLE_COMPRESSION);
+  visitor.SimulateInFramer(kH2Input, sizeof(kH2Input));
+
+  EXPECT_EQ(0, visitor.error_count_);
+  EXPECT_EQ(2, visitor.headers_frame_count_);
+  EXPECT_EQ(16, visitor.data_bytes_);
+  EXPECT_EQ(0, visitor.fin_frame_count_);
+  EXPECT_EQ(0, visitor.fin_flag_count_);
+  EXPECT_EQ(1, visitor.end_of_stream_count_);
+  EXPECT_EQ(2, visitor.data_frame_count_);
+}
+
+TEST_P(SpdyFramerTest, FinOnHeadersFrame) {
+  // Send HEADERS frames with END_HEADERS set.
+  // frame-format off
+  const unsigned char kH2Input[] = {
+      0x00, 0x00, 0x05,        // Length: 5
+      0x01,                    //   Type: HEADERS
+      0x24,                    //  Flags: END_HEADERS|PRIORITY
+      0x00, 0x00, 0x00, 0x01,  // Stream: 1
+      0x00, 0x00, 0x00, 0x00,  // Parent: 0
+      0x82,                    // Weight: 131
+
+      0x00, 0x00, 0x01,        // Length: 1
+      0x01,                    //   Type: HEADERS
+      0x05,                    //  Flags: END_STREAM|END_HEADERS
+      0x00, 0x00, 0x00, 0x01,  // Stream: 1
+      0x8c,                    // :status: 200
+  };
+  // frame-format on
+
+  TestSpdyVisitor visitor(SpdyFramer::DISABLE_COMPRESSION);
+  visitor.SimulateInFramer(kH2Input, sizeof(kH2Input));
+
+  EXPECT_EQ(0, visitor.error_count_);
+  EXPECT_EQ(2, visitor.headers_frame_count_);
+  EXPECT_EQ(0, visitor.data_bytes_);
+  EXPECT_EQ(0, visitor.fin_frame_count_);
+  EXPECT_EQ(1, visitor.fin_flag_count_);
+  EXPECT_EQ(1, visitor.end_of_stream_count_);
+  EXPECT_EQ(0, visitor.data_frame_count_);
+}
+
+// Verify we can decompress the stream even if handed over to the
+// framer 1 byte at a time.
+TEST_P(SpdyFramerTest, UnclosedStreamDataCompressorsOneByteAtATime) {
+  const char kHeader1[] = "header1";
+  const char kHeader2[] = "header2";
+  const char kValue1[] = "value1";
+  const char kValue2[] = "value2";
+
+  SpdyHeadersIR headers(/* stream_id = */ 1);
+  headers.SetHeader(kHeader1, kValue1);
+  headers.SetHeader(kHeader2, kValue2);
+  SpdySerializedFrame headers_frame(SpdyFramerPeer::SerializeHeaders(
+      &framer_, headers, use_output_ ? &output_ : nullptr));
+
+  const char bytes[] = "this is a test test test test test!";
+  SpdyDataIR data_ir(/* stream_id = */ 1,
+                     SpdyStringPiece(bytes, SPDY_ARRAYSIZE(bytes)));
+  data_ir.set_fin(true);
+  SpdySerializedFrame send_frame(framer_.SerializeData(data_ir));
+
+  // Run the inputs through the framer.
+  TestSpdyVisitor visitor(SpdyFramer::ENABLE_COMPRESSION);
+  const unsigned char* data;
+  data = reinterpret_cast<const unsigned char*>(headers_frame.data());
+  for (size_t idx = 0; idx < headers_frame.size(); ++idx) {
+    visitor.SimulateInFramer(data + idx, 1);
+    ASSERT_EQ(0, visitor.error_count_);
+  }
+  data = reinterpret_cast<const unsigned char*>(send_frame.data());
+  for (size_t idx = 0; idx < send_frame.size(); ++idx) {
+    visitor.SimulateInFramer(data + idx, 1);
+    ASSERT_EQ(0, visitor.error_count_);
+  }
+
+  EXPECT_EQ(0, visitor.error_count_);
+  EXPECT_EQ(1, visitor.headers_frame_count_);
+  EXPECT_EQ(SPDY_ARRAYSIZE(bytes), static_cast<unsigned>(visitor.data_bytes_));
+  EXPECT_EQ(0, visitor.fin_frame_count_);
+  EXPECT_EQ(0, visitor.fin_flag_count_);
+  EXPECT_EQ(1, visitor.end_of_stream_count_);
+  EXPECT_EQ(1, visitor.data_frame_count_);
+}
+
+TEST_P(SpdyFramerTest, WindowUpdateFrame) {
+  SpdyWindowUpdateIR window_update(/* stream_id = */ 1,
+                                   /* delta = */ 0x12345678);
+  SpdySerializedFrame frame(framer_.SerializeWindowUpdate(window_update));
+  if (use_output_) {
+    ASSERT_TRUE(framer_.SerializeWindowUpdate(window_update, &output_));
+    frame = SpdySerializedFrame(output_.Begin(), output_.Size(), false);
+  }
+
+  const char kDescription[] = "WINDOW_UPDATE frame, stream 1, delta 0x12345678";
+  const unsigned char kH2FrameData[] = {
+      0x00, 0x00, 0x04,        // Length: 4
+      0x08,                    //   Type: WINDOW_UPDATE
+      0x00,                    //  Flags: none
+      0x00, 0x00, 0x00, 0x01,  // Stream: 1
+      0x12, 0x34, 0x56, 0x78,  // Increment: 305419896
+  };
+
+  CompareFrame(kDescription, frame, kH2FrameData, SPDY_ARRAYSIZE(kH2FrameData));
+}
+
+TEST_P(SpdyFramerTest, CreateDataFrame) {
+  {
+    const char kDescription[] = "'hello' data frame, no FIN";
+    // frame-format off
+    const unsigned char kH2FrameData[] = {
+        0x00, 0x00, 0x05,        // Length: 5
+        0x00,                    //   Type: DATA
+        0x00,                    //  Flags: none
+        0x00, 0x00, 0x00, 0x01,  // Stream: 1
+        'h',  'e',  'l',  'l',   // Payload
+        'o',                     //
+    };
+    // frame-format on
+    const char bytes[] = "hello";
+
+    SpdyDataIR data_ir(/* stream_id = */ 1, bytes);
+    SpdySerializedFrame frame(framer_.SerializeData(data_ir));
+    CompareFrame(kDescription, frame, kH2FrameData,
+                 SPDY_ARRAYSIZE(kH2FrameData));
+
+    SpdyDataIR data_header_ir(/* stream_id = */ 1);
+    data_header_ir.SetDataShallow(bytes);
+    frame =
+        framer_.SerializeDataFrameHeaderWithPaddingLengthField(data_header_ir);
+    CompareCharArraysWithHexError(
+        kDescription, reinterpret_cast<const unsigned char*>(frame.data()),
+        kDataFrameMinimumSize, kH2FrameData, kDataFrameMinimumSize);
+  }
+
+  {
+    const char kDescription[] = "'hello' data frame with more padding, no FIN";
+    // clang-format off
+    // frame-format off
+    const unsigned char kH2FrameData[] = {
+        0x00, 0x00, 0xfd,        // Length: 253
+        0x00,                    //   Type: DATA
+        0x08,                    //  Flags: PADDED
+        0x00, 0x00, 0x00, 0x01,  // Stream: 1
+        0xf7,                    // PadLen: 247 trailing bytes
+        'h', 'e', 'l', 'l',      // Payload
+        'o',                     //
+        // Padding of 247 0x00(s).
+        0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+        0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+        0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+        0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+        0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+        0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+        0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+        0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+        0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+        0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+        0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+        0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+        0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+        0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+        0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+        0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+        0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+        0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+        0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+        0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+        0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+    };
+    // frame-format on
+    // clang-format on
+    const char bytes[] = "hello";
+
+    SpdyDataIR data_ir(/* stream_id = */ 1, bytes);
+    // 247 zeros and the pad length field make the overall padding to be 248
+    // bytes.
+    data_ir.set_padding_len(248);
+    SpdySerializedFrame frame(framer_.SerializeData(data_ir));
+    CompareFrame(kDescription, frame, kH2FrameData,
+                 SPDY_ARRAYSIZE(kH2FrameData));
+
+    frame = framer_.SerializeDataFrameHeaderWithPaddingLengthField(data_ir);
+    CompareCharArraysWithHexError(
+        kDescription, reinterpret_cast<const unsigned char*>(frame.data()),
+        kDataFrameMinimumSize, kH2FrameData, kDataFrameMinimumSize);
+  }
+
+  {
+    const char kDescription[] = "'hello' data frame with few padding, no FIN";
+    // frame-format off
+    const unsigned char kH2FrameData[] = {
+        0x00, 0x00, 0x0d,        // Length: 13
+        0x00,                    //   Type: DATA
+        0x08,                    //  Flags: PADDED
+        0x00, 0x00, 0x00, 0x01,  // Stream: 1
+        0x07,                    // PadLen: 7 trailing bytes
+        'h',  'e',  'l',  'l',   // Payload
+        'o',                     //
+        0x00, 0x00, 0x00, 0x00,  // Padding
+        0x00, 0x00, 0x00,        // Padding
+    };
+    // frame-format on
+    const char bytes[] = "hello";
+
+    SpdyDataIR data_ir(/* stream_id = */ 1, bytes);
+    // 7 zeros and the pad length field make the overall padding to be 8 bytes.
+    data_ir.set_padding_len(8);
+    SpdySerializedFrame frame(framer_.SerializeData(data_ir));
+    CompareFrame(kDescription, frame, kH2FrameData,
+                 SPDY_ARRAYSIZE(kH2FrameData));
+
+    frame = framer_.SerializeDataFrameHeaderWithPaddingLengthField(data_ir);
+    CompareCharArraysWithHexError(
+        kDescription, reinterpret_cast<const unsigned char*>(frame.data()),
+        kDataFrameMinimumSize, kH2FrameData, kDataFrameMinimumSize);
+  }
+
+  {
+    const char kDescription[] =
+        "'hello' data frame with 1 byte padding, no FIN";
+    // frame-format off
+    const unsigned char kH2FrameData[] = {
+        0x00, 0x00, 0x06,        // Length: 6
+        0x00,                    //   Type: DATA
+        0x08,                    //  Flags: PADDED
+        0x00, 0x00, 0x00, 0x01,  // Stream: 1
+        0x00,                    // PadLen: 0 trailing bytes
+        'h',  'e',  'l',  'l',   // Payload
+        'o',                     //
+    };
+    // frame-format on
+    const char bytes[] = "hello";
+
+    SpdyDataIR data_ir(/* stream_id = */ 1, bytes);
+    // The pad length field itself is used for the 1-byte padding and no padding
+    // payload is needed.
+    data_ir.set_padding_len(1);
+    SpdySerializedFrame frame(framer_.SerializeData(data_ir));
+    CompareFrame(kDescription, frame, kH2FrameData,
+                 SPDY_ARRAYSIZE(kH2FrameData));
+
+    frame = framer_.SerializeDataFrameHeaderWithPaddingLengthField(data_ir);
+    CompareCharArraysWithHexError(
+        kDescription, reinterpret_cast<const unsigned char*>(frame.data()),
+        kDataFrameMinimumSize, kH2FrameData, kDataFrameMinimumSize);
+  }
+
+  {
+    const char kDescription[] = "Data frame with negative data byte, no FIN";
+    const unsigned char kH2FrameData[] = {
+        0x00, 0x00, 0x01,        // Length: 1
+        0x00,                    //   Type: DATA
+        0x00,                    //  Flags: none
+        0x00, 0x00, 0x00, 0x01,  // Stream: 1
+        0xff,                    // Payload
+    };
+    SpdyDataIR data_ir(/* stream_id = */ 1, "\xff");
+    SpdySerializedFrame frame(framer_.SerializeData(data_ir));
+    CompareFrame(kDescription, frame, kH2FrameData,
+                 SPDY_ARRAYSIZE(kH2FrameData));
+  }
+
+  {
+    const char kDescription[] = "'hello' data frame, with FIN";
+    const unsigned char kH2FrameData[] = {
+        0x00, 0x00, 0x05,        // Length: 5
+        0x00,                    //   Type: DATA
+        0x01,                    //  Flags: END_STREAM
+        0x00, 0x00, 0x00, 0x01,  // Stream: 1
+        0x68, 0x65, 0x6c, 0x6c,  // Payload
+        0x6f,                    //
+    };
+    SpdyDataIR data_ir(/* stream_id = */ 1, "hello");
+    data_ir.set_fin(true);
+    SpdySerializedFrame frame(framer_.SerializeData(data_ir));
+    CompareFrame(kDescription, frame, kH2FrameData,
+                 SPDY_ARRAYSIZE(kH2FrameData));
+  }
+
+  {
+    const char kDescription[] = "Empty data frame";
+    const unsigned char kH2FrameData[] = {
+        0x00, 0x00, 0x00,        // Length: 0
+        0x00,                    //   Type: DATA
+        0x00,                    //  Flags: none
+        0x00, 0x00, 0x00, 0x01,  // Stream: 1
+    };
+    SpdyDataIR data_ir(/* stream_id = */ 1, "");
+    SpdySerializedFrame frame(framer_.SerializeData(data_ir));
+    CompareFrame(kDescription, frame, kH2FrameData,
+                 SPDY_ARRAYSIZE(kH2FrameData));
+
+    frame = framer_.SerializeDataFrameHeaderWithPaddingLengthField(data_ir);
+    CompareCharArraysWithHexError(
+        kDescription, reinterpret_cast<const unsigned char*>(frame.data()),
+        kDataFrameMinimumSize, kH2FrameData, kDataFrameMinimumSize);
+  }
+
+  {
+    const char kDescription[] = "Data frame with max stream ID";
+    const unsigned char kH2FrameData[] = {
+        0x00, 0x00, 0x05,        // Length: 5
+        0x00,                    //   Type: DATA
+        0x01,                    //  Flags: END_STREAM
+        0x7f, 0xff, 0xff, 0xff,  // Stream: 0x7fffffff
+        0x68, 0x65, 0x6c, 0x6c,  // Payload
+        0x6f,                    //
+    };
+    SpdyDataIR data_ir(/* stream_id = */ 0x7fffffff, "hello");
+    data_ir.set_fin(true);
+    SpdySerializedFrame frame(framer_.SerializeData(data_ir));
+    CompareFrame(kDescription, frame, kH2FrameData,
+                 SPDY_ARRAYSIZE(kH2FrameData));
+  }
+}
+
+TEST_P(SpdyFramerTest, CreateRstStream) {
+  {
+    const char kDescription[] = "RST_STREAM frame";
+    const unsigned char kH2FrameData[] = {
+        0x00, 0x00, 0x04,        // Length: 4
+        0x03,                    //   Type: RST_STREAM
+        0x00,                    //  Flags: none
+        0x00, 0x00, 0x00, 0x01,  // Stream: 1
+        0x00, 0x00, 0x00, 0x01,  //  Error: PROTOCOL_ERROR
+    };
+    SpdyRstStreamIR rst_stream(/* stream_id = */ 1, ERROR_CODE_PROTOCOL_ERROR);
+    SpdySerializedFrame frame(framer_.SerializeRstStream(rst_stream));
+    if (use_output_) {
+      ASSERT_TRUE(framer_.SerializeRstStream(rst_stream, &output_));
+      frame = SpdySerializedFrame(output_.Begin(), output_.Size(), false);
+    }
+    CompareFrame(kDescription, frame, kH2FrameData,
+                 SPDY_ARRAYSIZE(kH2FrameData));
+  }
+
+  {
+    const char kDescription[] = "RST_STREAM frame with max stream ID";
+    const unsigned char kH2FrameData[] = {
+        0x00, 0x00, 0x04,        // Length: 4
+        0x03,                    //   Type: RST_STREAM
+        0x00,                    //  Flags: none
+        0x7f, 0xff, 0xff, 0xff,  // Stream: 0x7fffffff
+        0x00, 0x00, 0x00, 0x01,  //  Error: PROTOCOL_ERROR
+    };
+    SpdyRstStreamIR rst_stream(/* stream_id = */ 0x7FFFFFFF,
+                               ERROR_CODE_PROTOCOL_ERROR);
+    SpdySerializedFrame frame(framer_.SerializeRstStream(rst_stream));
+    if (use_output_) {
+      output_.Reset();
+      ASSERT_TRUE(framer_.SerializeRstStream(rst_stream, &output_));
+      frame = SpdySerializedFrame(output_.Begin(), output_.Size(), false);
+    }
+    CompareFrame(kDescription, frame, kH2FrameData,
+                 SPDY_ARRAYSIZE(kH2FrameData));
+  }
+
+  {
+    const char kDescription[] = "RST_STREAM frame with max status code";
+    const unsigned char kH2FrameData[] = {
+        0x00, 0x00, 0x04,        // Length: 4
+        0x03,                    //   Type: RST_STREAM
+        0x00,                    //  Flags: none
+        0x7f, 0xff, 0xff, 0xff,  // Stream: 0x7fffffff
+        0x00, 0x00, 0x00, 0x02,  //  Error: INTERNAL_ERROR
+    };
+    SpdyRstStreamIR rst_stream(/* stream_id = */ 0x7FFFFFFF,
+                               ERROR_CODE_INTERNAL_ERROR);
+    SpdySerializedFrame frame(framer_.SerializeRstStream(rst_stream));
+    if (use_output_) {
+      output_.Reset();
+      ASSERT_TRUE(framer_.SerializeRstStream(rst_stream, &output_));
+      frame = SpdySerializedFrame(output_.Begin(), output_.Size(), false);
+    }
+    CompareFrame(kDescription, frame, kH2FrameData,
+                 SPDY_ARRAYSIZE(kH2FrameData));
+  }
+}
+
+TEST_P(SpdyFramerTest, CreateSettings) {
+  {
+    const char kDescription[] = "Network byte order SETTINGS frame";
+    const unsigned char kH2FrameData[] = {
+        0x00, 0x00, 0x06,        // Length: 6
+        0x04,                    //   Type: SETTINGS
+        0x00,                    //  Flags: none
+        0x00, 0x00, 0x00, 0x00,  // Stream: 0
+        0x00, 0x04,              //  Param: INITIAL_WINDOW_SIZE
+        0x0a, 0x0b, 0x0c, 0x0d,  //  Value: 168496141
+    };
+
+    uint32_t kValue = 0x0a0b0c0d;
+    SpdySettingsIR settings_ir;
+
+    SpdyKnownSettingsId kId = SETTINGS_INITIAL_WINDOW_SIZE;
+    settings_ir.AddSetting(kId, kValue);
+
+    SpdySerializedFrame frame(framer_.SerializeSettings(settings_ir));
+    if (use_output_) {
+      ASSERT_TRUE(framer_.SerializeSettings(settings_ir, &output_));
+      frame = SpdySerializedFrame(output_.Begin(), output_.Size(), false);
+    }
+    CompareFrame(kDescription, frame, kH2FrameData,
+                 SPDY_ARRAYSIZE(kH2FrameData));
+  }
+
+  {
+    const char kDescription[] = "Basic SETTINGS frame";
+    // These end up seemingly out of order because of the way that our internal
+    // ordering for settings_ir works. HTTP2 has no requirement on ordering on
+    // the wire.
+    const unsigned char kH2FrameData[] = {
+        0x00, 0x00, 0x18,        // Length: 24
+        0x04,                    //   Type: SETTINGS
+        0x00,                    //  Flags: none
+        0x00, 0x00, 0x00, 0x00,  // Stream: 0
+        0x00, 0x01,              //  Param: HEADER_TABLE_SIZE
+        0x00, 0x00, 0x00, 0x05,  //  Value: 5
+        0x00, 0x02,              //  Param: ENABLE_PUSH
+        0x00, 0x00, 0x00, 0x06,  //  Value: 6
+        0x00, 0x03,              //  Param: MAX_CONCURRENT_STREAMS
+        0x00, 0x00, 0x00, 0x07,  //  Value: 7
+        0x00, 0x04,              //  Param: INITIAL_WINDOW_SIZE
+        0x00, 0x00, 0x00, 0x08,  //  Value: 8
+    };
+
+    SpdySettingsIR settings_ir;
+    settings_ir.AddSetting(SETTINGS_HEADER_TABLE_SIZE, 5);
+    settings_ir.AddSetting(SETTINGS_ENABLE_PUSH, 6);
+    settings_ir.AddSetting(SETTINGS_MAX_CONCURRENT_STREAMS, 7);
+    settings_ir.AddSetting(SETTINGS_INITIAL_WINDOW_SIZE, 8);
+    SpdySerializedFrame frame(framer_.SerializeSettings(settings_ir));
+    if (use_output_) {
+      output_.Reset();
+      ASSERT_TRUE(framer_.SerializeSettings(settings_ir, &output_));
+      frame = SpdySerializedFrame(output_.Begin(), output_.Size(), false);
+    }
+
+    CompareFrame(kDescription, frame, kH2FrameData,
+                 SPDY_ARRAYSIZE(kH2FrameData));
+  }
+
+  {
+    const char kDescription[] = "Empty SETTINGS frame";
+    const unsigned char kH2FrameData[] = {
+        0x00, 0x00, 0x00,        // Length: 0
+        0x04,                    //   Type: SETTINGS
+        0x00,                    //  Flags: none
+        0x00, 0x00, 0x00, 0x00,  // Stream: 0
+    };
+    SpdySettingsIR settings_ir;
+    SpdySerializedFrame frame(framer_.SerializeSettings(settings_ir));
+    if (use_output_) {
+      output_.Reset();
+      ASSERT_TRUE(framer_.SerializeSettings(settings_ir, &output_));
+      frame = SpdySerializedFrame(output_.Begin(), output_.Size(), false);
+    }
+
+    CompareFrame(kDescription, frame, kH2FrameData,
+                 SPDY_ARRAYSIZE(kH2FrameData));
+  }
+}
+
+TEST_P(SpdyFramerTest, CreatePingFrame) {
+  {
+    const char kDescription[] = "PING frame";
+    const unsigned char kH2FrameData[] = {
+        0x00, 0x00, 0x08,        // Length: 8
+        0x06,                    //   Type: PING
+        0x00,                    //  Flags: none
+        0x00, 0x00, 0x00, 0x00,  // Stream: 0
+        0x12, 0x34, 0x56, 0x78,  // Opaque
+        0x9a, 0xbc, 0xde, 0xff,  //     Data
+    };
+    const unsigned char kH2FrameDataWithAck[] = {
+        0x00, 0x00, 0x08,        // Length: 8
+        0x06,                    //   Type: PING
+        0x01,                    //  Flags: ACK
+        0x00, 0x00, 0x00, 0x00,  // Stream: 0
+        0x12, 0x34, 0x56, 0x78,  // Opaque
+        0x9a, 0xbc, 0xde, 0xff,  //     Data
+    };
+    const SpdyPingId kPingId = 0x123456789abcdeffULL;
+    SpdyPingIR ping_ir(kPingId);
+    // Tests SpdyPingIR when the ping is not an ack.
+    ASSERT_FALSE(ping_ir.is_ack());
+    SpdySerializedFrame frame(framer_.SerializePing(ping_ir));
+    if (use_output_) {
+      ASSERT_TRUE(framer_.SerializePing(ping_ir, &output_));
+      frame = SpdySerializedFrame(output_.Begin(), output_.Size(), false);
+    }
+    CompareFrame(kDescription, frame, kH2FrameData,
+                 SPDY_ARRAYSIZE(kH2FrameData));
+
+    // Tests SpdyPingIR when the ping is an ack.
+    ping_ir.set_is_ack(true);
+    frame = framer_.SerializePing(ping_ir);
+    if (use_output_) {
+      output_.Reset();
+      ASSERT_TRUE(framer_.SerializePing(ping_ir, &output_));
+      frame = SpdySerializedFrame(output_.Begin(), output_.Size(), false);
+    }
+    CompareFrame(kDescription, frame, kH2FrameDataWithAck,
+                 SPDY_ARRAYSIZE(kH2FrameDataWithAck));
+  }
+}
+
+TEST_P(SpdyFramerTest, CreateGoAway) {
+  {
+    const char kDescription[] = "GOAWAY frame";
+    const unsigned char kH2FrameData[] = {
+        0x00, 0x00, 0x0a,        // Length: 10
+        0x07,                    //   Type: GOAWAY
+        0x00,                    //  Flags: none
+        0x00, 0x00, 0x00, 0x00,  // Stream: 0
+        0x00, 0x00, 0x00, 0x00,  //   Last: 0
+        0x00, 0x00, 0x00, 0x00,  //  Error: NO_ERROR
+        0x47, 0x41,              // Description
+    };
+    SpdyGoAwayIR goaway_ir(/* last_good_stream_id = */ 0, ERROR_CODE_NO_ERROR,
+                           "GA");
+    SpdySerializedFrame frame(framer_.SerializeGoAway(goaway_ir));
+    if (use_output_) {
+      ASSERT_TRUE(framer_.SerializeGoAway(goaway_ir, &output_));
+      frame = SpdySerializedFrame(output_.Begin(), output_.Size(), false);
+    }
+    CompareFrame(kDescription, frame, kH2FrameData,
+                 SPDY_ARRAYSIZE(kH2FrameData));
+  }
+
+  {
+    const char kDescription[] = "GOAWAY frame with max stream ID, status";
+    const unsigned char kH2FrameData[] = {
+        0x00, 0x00, 0x0a,        // Length: 10
+        0x07,                    //   Type: GOAWAY
+        0x00,                    //  Flags: none
+        0x00, 0x00, 0x00, 0x00,  // Stream: 0
+        0x7f, 0xff, 0xff, 0xff,  //   Last: 0x7fffffff
+        0x00, 0x00, 0x00, 0x02,  //  Error: INTERNAL_ERROR
+        0x47, 0x41,              // Description
+    };
+    SpdyGoAwayIR goaway_ir(/* last_good_stream_id = */ 0x7FFFFFFF,
+                           ERROR_CODE_INTERNAL_ERROR, "GA");
+    SpdySerializedFrame frame(framer_.SerializeGoAway(goaway_ir));
+    if (use_output_) {
+      output_.Reset();
+      ASSERT_TRUE(framer_.SerializeGoAway(goaway_ir, &output_));
+      frame = SpdySerializedFrame(output_.Begin(), output_.Size(), false);
+    }
+    CompareFrame(kDescription, frame, kH2FrameData,
+                 SPDY_ARRAYSIZE(kH2FrameData));
+  }
+}
+
+TEST_P(SpdyFramerTest, CreateHeadersUncompressed) {
+  SpdyFramer framer(SpdyFramer::DISABLE_COMPRESSION);
+
+  {
+    const char kDescription[] = "HEADERS frame, no FIN";
+    // frame-format off
+    const unsigned char kH2FrameData[] = {
+        0x00, 0x00, 0x12,        // Length: 18
+        0x01,                    //   Type: HEADERS
+        0x04,                    //  Flags: END_HEADERS
+        0x00, 0x00, 0x00, 0x01,  // Stream: 1
+
+        0x00,              // Unindexed Entry
+        0x03,              // Name Len: 3
+        0x62, 0x61, 0x72,  // bar
+        0x03,              // Value Len: 3
+        0x66, 0x6f, 0x6f,  // foo
+
+        0x00,              // Unindexed Entry
+        0x03,              // Name Len: 3
+        0x66, 0x6f, 0x6f,  // foo
+        0x03,              // Value Len: 3
+        0x62, 0x61, 0x72,  // bar
+    };
+    // frame-format on
+    SpdyHeadersIR headers(/* stream_id = */ 1);
+    headers.SetHeader("bar", "foo");
+    headers.SetHeader("foo", "bar");
+    SpdySerializedFrame frame(SpdyFramerPeer::SerializeHeaders(
+        &framer, headers, use_output_ ? &output_ : nullptr));
+    CompareFrame(kDescription, frame, kH2FrameData,
+                 SPDY_ARRAYSIZE(kH2FrameData));
+  }
+
+  {
+    const char kDescription[] =
+        "HEADERS frame with a 0-length header name, FIN, max stream ID";
+    // frame-format off
+    const unsigned char kH2FrameData[] = {
+        0x00, 0x00, 0x0f,        // Length: 15
+        0x01,                    //   Type: HEADERS
+        0x05,                    //  Flags: END_STREAM|END_HEADERS
+        0x7f, 0xff, 0xff, 0xff,  // Stream: 2147483647
+
+        0x00,              // Unindexed Entry
+        0x00,              // Name Len: 0
+        0x03,              // Value Len: 3
+        0x66, 0x6f, 0x6f,  // foo
+
+        0x00,              // Unindexed Entry
+        0x03,              // Name Len: 3
+        0x66, 0x6f, 0x6f,  // foo
+        0x03,              // Value Len: 3
+        0x62, 0x61, 0x72,  // bar
+    };
+    // frame-format on
+    SpdyHeadersIR headers(/* stream_id = */ 0x7fffffff);
+    headers.set_fin(true);
+    headers.SetHeader("", "foo");
+    headers.SetHeader("foo", "bar");
+    SpdySerializedFrame frame(SpdyFramerPeer::SerializeHeaders(
+        &framer, headers, use_output_ ? &output_ : nullptr));
+    CompareFrame(kDescription, frame, kH2FrameData,
+                 SPDY_ARRAYSIZE(kH2FrameData));
+  }
+
+  {
+    const char kDescription[] =
+        "HEADERS frame with a 0-length header val, FIN, max stream ID";
+    // frame-format off
+    const unsigned char kH2FrameData[] = {
+        0x00, 0x00, 0x0f,        // Length: 15
+        0x01,                    //   Type: HEADERS
+        0x05,                    //  Flags: END_STREAM|END_HEADERS
+        0x7f, 0xff, 0xff, 0xff,  // Stream: 2147483647
+
+        0x00,              // Unindexed Entry
+        0x03,              // Name Len: 3
+        0x62, 0x61, 0x72,  // bar
+        0x03,              // Value Len: 3
+        0x66, 0x6f, 0x6f,  // foo
+
+        0x00,              // Unindexed Entry
+        0x03,              // Name Len: 3
+        0x66, 0x6f, 0x6f,  // foo
+        0x00,              // Value Len: 0
+    };
+    // frame-format on
+    SpdyHeadersIR headers_ir(/* stream_id = */ 0x7fffffff);
+    headers_ir.set_fin(true);
+    headers_ir.SetHeader("bar", "foo");
+    headers_ir.SetHeader("foo", "");
+    SpdySerializedFrame frame(SpdyFramerPeer::SerializeHeaders(
+        &framer, headers_ir, use_output_ ? &output_ : nullptr));
+    CompareFrame(kDescription, frame, kH2FrameData,
+                 SPDY_ARRAYSIZE(kH2FrameData));
+  }
+
+  {
+    const char kDescription[] =
+        "HEADERS frame with a 0-length header val, FIN, max stream ID, pri";
+
+    // frame-format off
+    const unsigned char kH2FrameData[] = {
+        0x00, 0x00, 0x14,        // Length: 20
+        0x01,                    //   Type: HEADERS
+        0x25,                    //  Flags: END_STREAM|END_HEADERS|PRIORITY
+        0x7f, 0xff, 0xff, 0xff,  // Stream: 2147483647
+        0x00, 0x00, 0x00, 0x00,  // Parent: 0
+        0xdb,                    // Weight: 220
+
+        0x00,              // Unindexed Entry
+        0x03,              // Name Len: 3
+        0x62, 0x61, 0x72,  // bar
+        0x03,              // Value Len: 3
+        0x66, 0x6f, 0x6f,  // foo
+
+        0x00,              // Unindexed Entry
+        0x03,              // Name Len: 3
+        0x66, 0x6f, 0x6f,  // foo
+        0x00,              // Value Len: 0
+    };
+    // frame-format on
+    SpdyHeadersIR headers_ir(/* stream_id = */ 0x7fffffff);
+    headers_ir.set_fin(true);
+    headers_ir.set_has_priority(true);
+    headers_ir.set_weight(220);
+    headers_ir.SetHeader("bar", "foo");
+    headers_ir.SetHeader("foo", "");
+    SpdySerializedFrame frame(SpdyFramerPeer::SerializeHeaders(
+        &framer, headers_ir, use_output_ ? &output_ : nullptr));
+    CompareFrame(kDescription, frame, kH2FrameData,
+                 SPDY_ARRAYSIZE(kH2FrameData));
+  }
+
+  {
+    const char kDescription[] =
+        "HEADERS frame with a 0-length header val, FIN, max stream ID, pri, "
+        "exclusive=true, parent_stream=0";
+
+    // frame-format off
+    const unsigned char kV4FrameData[] = {
+        0x00, 0x00, 0x14,        // Length: 20
+        0x01,                    //   Type: HEADERS
+        0x25,                    //  Flags: END_STREAM|END_HEADERS|PRIORITY
+        0x7f, 0xff, 0xff, 0xff,  // Stream: 2147483647
+        0x80, 0x00, 0x00, 0x00,  // Parent: 0 (Exclusive)
+        0xdb,                    // Weight: 220
+
+        0x00,              // Unindexed Entry
+        0x03,              // Name Len: 3
+        0x62, 0x61, 0x72,  // bar
+        0x03,              // Value Len: 3
+        0x66, 0x6f, 0x6f,  // foo
+
+        0x00,              // Unindexed Entry
+        0x03,              // Name Len: 3
+        0x66, 0x6f, 0x6f,  // foo
+        0x00,              // Value Len: 0
+    };
+    // frame-format on
+    SpdyHeadersIR headers_ir(/* stream_id = */ 0x7fffffff);
+    headers_ir.set_fin(true);
+    headers_ir.set_has_priority(true);
+    headers_ir.set_weight(220);
+    headers_ir.set_exclusive(true);
+    headers_ir.set_parent_stream_id(0);
+    headers_ir.SetHeader("bar", "foo");
+    headers_ir.SetHeader("foo", "");
+    SpdySerializedFrame frame(SpdyFramerPeer::SerializeHeaders(
+        &framer, headers_ir, use_output_ ? &output_ : nullptr));
+    CompareFrame(kDescription, frame, kV4FrameData,
+                 SPDY_ARRAYSIZE(kV4FrameData));
+  }
+
+  {
+    const char kDescription[] =
+        "HEADERS frame with a 0-length header val, FIN, max stream ID, pri, "
+        "exclusive=false, parent_stream=max stream ID";
+
+    // frame-format off
+    const unsigned char kV4FrameData[] = {
+        0x00, 0x00, 0x14,        // Length: 20
+        0x01,                    //   Type: HEADERS
+        0x25,                    //  Flags: END_STREAM|END_HEADERS|PRIORITY
+        0x7f, 0xff, 0xff, 0xff,  // Stream: 2147483647
+        0x7f, 0xff, 0xff, 0xff,  // Parent: 2147483647
+        0xdb,                    // Weight: 220
+
+        0x00,              // Unindexed Entry
+        0x03,              // Name Len: 3
+        0x62, 0x61, 0x72,  // bar
+        0x03,              // Value Len: 3
+        0x66, 0x6f, 0x6f,  // foo
+
+        0x00,              // Unindexed Entry
+        0x03,              // Name Len: 3
+        0x66, 0x6f, 0x6f,  // foo
+        0x00,              // Value Len: 0
+    };
+    // frame-format on
+    SpdyHeadersIR headers_ir(/* stream_id = */ 0x7fffffff);
+    headers_ir.set_fin(true);
+    headers_ir.set_has_priority(true);
+    headers_ir.set_weight(220);
+    headers_ir.set_exclusive(false);
+    headers_ir.set_parent_stream_id(0x7fffffff);
+    headers_ir.SetHeader("bar", "foo");
+    headers_ir.SetHeader("foo", "");
+    SpdySerializedFrame frame(SpdyFramerPeer::SerializeHeaders(
+        &framer, headers_ir, use_output_ ? &output_ : nullptr));
+    CompareFrame(kDescription, frame, kV4FrameData,
+                 SPDY_ARRAYSIZE(kV4FrameData));
+  }
+
+  {
+    const char kDescription[] =
+        "HEADERS frame with a 0-length header name, FIN, max stream ID, padded";
+
+    // frame-format off
+    const unsigned char kH2FrameData[] = {
+        0x00, 0x00, 0x15,        // Length: 21
+        0x01,                    //   Type: HEADERS
+        0x0d,                    //  Flags: END_STREAM|END_HEADERS|PADDED
+        0x7f, 0xff, 0xff, 0xff,  // Stream: 2147483647
+        0x05,                    // PadLen: 5 trailing bytes
+
+        0x00,              // Unindexed Entry
+        0x00,              // Name Len: 0
+        0x03,              // Value Len: 3
+        0x66, 0x6f, 0x6f,  // foo
+
+        0x00,              // Unindexed Entry
+        0x03,              // Name Len: 3
+        0x66, 0x6f, 0x6f,  // foo
+        0x03,              // Value Len: 3
+        0x62, 0x61, 0x72,  // bar
+
+        0x00, 0x00, 0x00, 0x00,  // Padding
+        0x00,                    // Padding
+    };
+    // frame-format on
+    SpdyHeadersIR headers_ir(/* stream_id = */ 0x7fffffff);
+    headers_ir.set_fin(true);
+    headers_ir.SetHeader("", "foo");
+    headers_ir.SetHeader("foo", "bar");
+    headers_ir.set_padding_len(6);
+    SpdySerializedFrame frame(SpdyFramerPeer::SerializeHeaders(
+        &framer, headers_ir, use_output_ ? &output_ : nullptr));
+    CompareFrame(kDescription, frame, kH2FrameData,
+                 SPDY_ARRAYSIZE(kH2FrameData));
+  }
+}
+
+TEST_P(SpdyFramerTest, CreateWindowUpdate) {
+  {
+    const char kDescription[] = "WINDOW_UPDATE frame";
+    const unsigned char kH2FrameData[] = {
+        0x00, 0x00, 0x04,        // Length: 4
+        0x08,                    //   Type: WINDOW_UPDATE
+        0x00,                    //  Flags: none
+        0x00, 0x00, 0x00, 0x01,  // Stream: 1
+        0x00, 0x00, 0x00, 0x01,  // Increment: 1
+    };
+    SpdySerializedFrame frame(framer_.SerializeWindowUpdate(
+        SpdyWindowUpdateIR(/* stream_id = */ 1, /* delta = */ 1)));
+    if (use_output_) {
+      output_.Reset();
+      ASSERT_TRUE(framer_.SerializeWindowUpdate(
+          SpdyWindowUpdateIR(/* stream_id = */ 1, /* delta = */ 1), &output_));
+      frame = SpdySerializedFrame(output_.Begin(), output_.Size(), false);
+    }
+    CompareFrame(kDescription, frame, kH2FrameData,
+                 SPDY_ARRAYSIZE(kH2FrameData));
+  }
+
+  {
+    const char kDescription[] = "WINDOW_UPDATE frame with max stream ID";
+    const unsigned char kH2FrameData[] = {
+        0x00, 0x00, 0x04,        // Length: 4
+        0x08,                    //   Type: WINDOW_UPDATE
+        0x00,                    //  Flags: none
+        0x7f, 0xff, 0xff, 0xff,  // Stream: 0x7fffffff
+        0x00, 0x00, 0x00, 0x01,  // Increment: 1
+    };
+    SpdySerializedFrame frame(framer_.SerializeWindowUpdate(
+        SpdyWindowUpdateIR(/* stream_id = */ 0x7FFFFFFF, /* delta = */ 1)));
+    if (use_output_) {
+      output_.Reset();
+      ASSERT_TRUE(framer_.SerializeWindowUpdate(
+          SpdyWindowUpdateIR(/* stream_id = */ 0x7FFFFFFF, /* delta = */ 1),
+          &output_));
+      frame = SpdySerializedFrame(output_.Begin(), output_.Size(), false);
+    }
+    CompareFrame(kDescription, frame, kH2FrameData,
+                 SPDY_ARRAYSIZE(kH2FrameData));
+  }
+
+  {
+    const char kDescription[] = "WINDOW_UPDATE frame with max window delta";
+    const unsigned char kH2FrameData[] = {
+        0x00, 0x00, 0x04,        // Length: 4
+        0x08,                    //   Type: WINDOW_UPDATE
+        0x00,                    //  Flags: none
+        0x00, 0x00, 0x00, 0x01,  // Stream: 1
+        0x7f, 0xff, 0xff, 0xff,  // Increment: 0x7fffffff
+    };
+    SpdySerializedFrame frame(framer_.SerializeWindowUpdate(
+        SpdyWindowUpdateIR(/* stream_id = */ 1, /* delta = */ 0x7FFFFFFF)));
+    if (use_output_) {
+      output_.Reset();
+      ASSERT_TRUE(framer_.SerializeWindowUpdate(
+          SpdyWindowUpdateIR(/* stream_id = */ 1, /* delta = */ 0x7FFFFFFF),
+          &output_));
+      frame = SpdySerializedFrame(output_.Begin(), output_.Size(), false);
+    }
+    CompareFrame(kDescription, frame, kH2FrameData,
+                 SPDY_ARRAYSIZE(kH2FrameData));
+  }
+}
+
+TEST_P(SpdyFramerTest, CreatePushPromiseUncompressed) {
+  {
+    // Test framing PUSH_PROMISE without padding.
+    SpdyFramer framer(SpdyFramer::DISABLE_COMPRESSION);
+    const char kDescription[] = "PUSH_PROMISE frame without padding";
+
+    // frame-format off
+    const unsigned char kFrameData[] = {
+        0x00, 0x00, 0x16,        // Length: 22
+        0x05,                    //   Type: PUSH_PROMISE
+        0x04,                    //  Flags: END_HEADERS
+        0x00, 0x00, 0x00, 0x29,  // Stream: 41
+        0x00, 0x00, 0x00, 0x3a,  // Promise: 58
+
+        0x00,              // Unindexed Entry
+        0x03,              // Name Len: 3
+        0x62, 0x61, 0x72,  // bar
+        0x03,              // Value Len: 3
+        0x66, 0x6f, 0x6f,  // foo
+
+        0x00,              // Unindexed Entry
+        0x03,              // Name Len: 3
+        0x66, 0x6f, 0x6f,  // foo
+        0x03,              // Value Len: 3
+        0x62, 0x61, 0x72,  // bar
+    };
+    // frame-format on
+
+    SpdyPushPromiseIR push_promise(/* stream_id = */ 41,
+                                   /* promised_stream_id = */ 58);
+    push_promise.SetHeader("bar", "foo");
+    push_promise.SetHeader("foo", "bar");
+    SpdySerializedFrame frame(SpdyFramerPeer::SerializePushPromise(
+        &framer, push_promise, use_output_ ? &output_ : nullptr));
+    CompareFrame(kDescription, frame, kFrameData, SPDY_ARRAYSIZE(kFrameData));
+  }
+
+  {
+    // Test framing PUSH_PROMISE with one byte of padding.
+    SpdyFramer framer(SpdyFramer::DISABLE_COMPRESSION);
+    const char kDescription[] = "PUSH_PROMISE frame with one byte of padding";
+
+    // frame-format off
+    const unsigned char kFrameData[] = {
+        0x00, 0x00, 0x17,        // Length: 23
+        0x05,                    //   Type: PUSH_PROMISE
+        0x0c,                    //  Flags: END_HEADERS|PADDED
+        0x00, 0x00, 0x00, 0x29,  // Stream: 41
+        0x00,                    // PadLen: 0 trailing bytes
+        0x00, 0x00, 0x00, 0x3a,  // Promise: 58
+
+        0x00,              // Unindexed Entry
+        0x03,              // Name Len: 3
+        0x62, 0x61, 0x72,  // bar
+        0x03,              // Value Len: 3
+        0x66, 0x6f, 0x6f,  // foo
+
+        0x00,              // Unindexed Entry
+        0x03,              // Name Len: 3
+        0x66, 0x6f, 0x6f,  // foo
+        0x03,              // Value Len: 3
+        0x62, 0x61, 0x72,  // bar
+    };
+    // frame-format on
+
+    SpdyPushPromiseIR push_promise(/* stream_id = */ 41,
+                                   /* promised_stream_id = */ 58);
+    push_promise.set_padding_len(1);
+    push_promise.SetHeader("bar", "foo");
+    push_promise.SetHeader("foo", "bar");
+    output_.Reset();
+    SpdySerializedFrame frame(SpdyFramerPeer::SerializePushPromise(
+        &framer, push_promise, use_output_ ? &output_ : nullptr));
+
+    CompareFrame(kDescription, frame, kFrameData, SPDY_ARRAYSIZE(kFrameData));
+  }
+
+  {
+    // Test framing PUSH_PROMISE with 177 bytes of padding.
+    SpdyFramer framer(SpdyFramer::DISABLE_COMPRESSION);
+    const char kDescription[] = "PUSH_PROMISE frame with 177 bytes of padding";
+
+    // frame-format off
+    // clang-format off
+    const unsigned char kFrameData[] = {
+        0x00, 0x00, 0xc7,        // Length: 199
+        0x05,                    //   Type: PUSH_PROMISE
+        0x0c,                    //  Flags: END_HEADERS|PADDED
+        0x00, 0x00, 0x00, 0x2a,  // Stream: 42
+        0xb0,                    // PadLen: 176 trailing bytes
+        0x00, 0x00, 0x00, 0x39,  // Promise: 57
+
+        0x00,                    // Unindexed Entry
+        0x03,                    // Name Len: 3
+        0x62, 0x61, 0x72,        // bar
+        0x03,                    // Value Len: 3
+        0x66, 0x6f, 0x6f,        // foo
+
+        0x00,                    // Unindexed Entry
+        0x03,                    // Name Len: 3
+        0x66, 0x6f, 0x6f,        // foo
+        0x03,                    // Value Len: 3
+        0x62, 0x61, 0x72,        // bar
+
+      // Padding of 176 0x00(s).
+      0x00,  0x00,  0x00,  0x00,  0x00,  0x00,  0x00,  0x00, 0x00,  0x00,  0x00,
+      0x00,  0x00,  0x00,  0x00,  0x00,  0x00,  0x00,  0x00, 0x00,  0x00,  0x00,
+      0x00,  0x00,  0x00,  0x00,  0x00,  0x00,  0x00,  0x00, 0x00,  0x00,  0x00,
+      0x00,  0x00,  0x00,  0x00,  0x00,  0x00,  0x00,  0x00, 0x00,  0x00,  0x00,
+      0x00,  0x00,  0x00,  0x00,  0x00,  0x00,  0x00,  0x00, 0x00,  0x00,  0x00,
+      0x00,  0x00,  0x00,  0x00,  0x00,  0x00,  0x00,  0x00, 0x00,  0x00,  0x00,
+      0x00,  0x00,  0x00,  0x00,  0x00,  0x00,  0x00,  0x00, 0x00,  0x00,  0x00,
+      0x00,  0x00,  0x00,  0x00,  0x00,  0x00,  0x00,  0x00, 0x00,  0x00,  0x00,
+      0x00,  0x00,  0x00,  0x00,  0x00,  0x00,  0x00,  0x00, 0x00,  0x00,  0x00,
+      0x00,  0x00,  0x00,  0x00,  0x00,  0x00,  0x00,  0x00, 0x00,  0x00,  0x00,
+      0x00,  0x00,  0x00,  0x00,  0x00,  0x00,  0x00,  0x00, 0x00,  0x00,  0x00,
+      0x00,  0x00,  0x00,  0x00,  0x00,  0x00,  0x00,  0x00, 0x00,  0x00,  0x00,
+      0x00,  0x00,  0x00,  0x00,  0x00,  0x00,  0x00,  0x00, 0x00,  0x00,  0x00,
+      0x00,  0x00,  0x00,  0x00,  0x00,  0x00,  0x00,  0x00, 0x00,  0x00,  0x00,
+      0x00,  0x00,  0x00,  0x00,  0x00,  0x00,  0x00,  0x00, 0x00,  0x00,  0x00,
+      0x00,  0x00,  0x00,  0x00,  0x00,  0x00,  0x00,  0x00, 0x00,  0x00,  0x00,
+    };
+    // clang-format on
+    // frame-format on
+
+    SpdyPushPromiseIR push_promise(/* stream_id = */ 42,
+                                   /* promised_stream_id = */ 57);
+    push_promise.set_padding_len(177);
+    push_promise.SetHeader("bar", "foo");
+    push_promise.SetHeader("foo", "bar");
+    output_.Reset();
+    SpdySerializedFrame frame(SpdyFramerPeer::SerializePushPromise(
+        &framer, push_promise, use_output_ ? &output_ : nullptr));
+
+    CompareFrame(kDescription, frame, kFrameData, SPDY_ARRAYSIZE(kFrameData));
+  }
+}
+
+// Regression test for https://crbug.com/464748.
+TEST_P(SpdyFramerTest, GetNumberRequiredContinuationFrames) {
+  EXPECT_EQ(1u, GetNumberRequiredContinuationFrames(16383 + 16374));
+  EXPECT_EQ(2u, GetNumberRequiredContinuationFrames(16383 + 16374 + 1));
+  EXPECT_EQ(2u, GetNumberRequiredContinuationFrames(16383 + 2 * 16374));
+  EXPECT_EQ(3u, GetNumberRequiredContinuationFrames(16383 + 2 * 16374 + 1));
+}
+
+TEST_P(SpdyFramerTest, CreateContinuationUncompressed) {
+  SpdyFramer framer(SpdyFramer::DISABLE_COMPRESSION);
+  const char kDescription[] = "CONTINUATION frame";
+
+  // frame-format off
+  const unsigned char kFrameData[] = {
+      0x00, 0x00, 0x12,        // Length: 18
+      0x09,                    //   Type: CONTINUATION
+      0x04,                    //  Flags: END_HEADERS
+      0x00, 0x00, 0x00, 0x2a,  // Stream: 42
+
+      0x00,              // Unindexed Entry
+      0x03,              // Name Len: 3
+      0x62, 0x61, 0x72,  // bar
+      0x03,              // Value Len: 3
+      0x66, 0x6f, 0x6f,  // foo
+
+      0x00,              // Unindexed Entry
+      0x03,              // Name Len: 3
+      0x66, 0x6f, 0x6f,  // foo
+      0x03,              // Value Len: 3
+      0x62, 0x61, 0x72,  // bar
+  };
+  // frame-format on
+
+  SpdyHeaderBlock header_block;
+  header_block["bar"] = "foo";
+  header_block["foo"] = "bar";
+  auto buffer = SpdyMakeUnique<SpdyString>();
+  HpackEncoder encoder(ObtainHpackHuffmanTable());
+  encoder.DisableCompression();
+  encoder.EncodeHeaderSet(header_block, buffer.get());
+
+  SpdyContinuationIR continuation(/* stream_id = */ 42);
+  continuation.take_encoding(std::move(buffer));
+  continuation.set_end_headers(true);
+
+  SpdySerializedFrame frame(framer.SerializeContinuation(continuation));
+  if (use_output_) {
+    ASSERT_TRUE(framer.SerializeContinuation(continuation, &output_));
+    frame = SpdySerializedFrame(output_.Begin(), output_.Size(), false);
+  }
+  CompareFrame(kDescription, frame, kFrameData, SPDY_ARRAYSIZE(kFrameData));
+}
+
+// Test that if we send an unexpected CONTINUATION
+// we signal an error (but don't crash).
+TEST_P(SpdyFramerTest, SendUnexpectedContinuation) {
+  testing::StrictMock<test::MockSpdyFramerVisitor> visitor;
+
+  deframer_.set_visitor(&visitor);
+
+  // frame-format off
+  char kH2FrameData[] = {
+      0x00, 0x00, 0x12,        // Length: 18
+      0x09,                    //   Type: CONTINUATION
+      0x04,                    //  Flags: END_HEADERS
+      0x00, 0x00, 0x00, 0x2a,  // Stream: 42
+
+      0x00,              // Unindexed Entry
+      0x03,              // Name Len: 3
+      0x62, 0x61, 0x72,  // bar
+      0x03,              // Value Len: 3
+      0x66, 0x6f, 0x6f,  // foo
+
+      0x00,              // Unindexed Entry
+      0x03,              // Name Len: 3
+      0x66, 0x6f, 0x6f,  // foo
+      0x03,              // Value Len: 3
+      0x62, 0x61, 0x72,  // bar
+  };
+  // frame-format on
+
+  SpdySerializedFrame frame(kH2FrameData, sizeof(kH2FrameData), false);
+
+  // We shouldn't have to read the whole frame before we signal an error.
+  EXPECT_CALL(visitor, OnError(Http2DecoderAdapter::SPDY_UNEXPECTED_FRAME));
+  EXPECT_GT(frame.size(), deframer_.ProcessInput(frame.data(), frame.size()));
+  EXPECT_TRUE(deframer_.HasError());
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_UNEXPECTED_FRAME,
+            deframer_.spdy_framer_error())
+      << Http2DecoderAdapter::SpdyFramerErrorToString(
+             deframer_.spdy_framer_error());
+}
+
+TEST_P(SpdyFramerTest, CreatePushPromiseThenContinuationUncompressed) {
+  {
+    // Test framing in a case such that a PUSH_PROMISE frame, with one byte of
+    // padding, cannot hold all the data payload, which is overflowed to the
+    // consecutive CONTINUATION frame.
+    SpdyFramer framer(SpdyFramer::DISABLE_COMPRESSION);
+    const char kDescription[] =
+        "PUSH_PROMISE and CONTINUATION frames with one byte of padding";
+
+    // frame-format off
+    const unsigned char kPartialPushPromiseFrameData[] = {
+        0x00, 0x3f, 0xf6,        // Length: 16374
+        0x05,                    //   Type: PUSH_PROMISE
+        0x08,                    //  Flags: PADDED
+        0x00, 0x00, 0x00, 0x2a,  // Stream: 42
+        0x00,                    // PadLen: 0 trailing bytes
+        0x00, 0x00, 0x00, 0x39,  // Promise: 57
+
+        0x00,                    // Unindexed Entry
+        0x03,                    // Name Len: 3
+        0x78, 0x78, 0x78,        // xxx
+        0x7f, 0x80, 0x7f,        // Value Len: 16361
+        0x78, 0x78, 0x78, 0x78,  // xxxx
+        0x78, 0x78, 0x78, 0x78,  // xxxx
+        0x78, 0x78, 0x78, 0x78,  // xxxx
+        0x78, 0x78, 0x78, 0x78,  // xxxx
+        0x78, 0x78, 0x78, 0x78,  // xxxx
+        0x78, 0x78, 0x78, 0x78,  // xxxx
+        0x78, 0x78, 0x78, 0x78,  // xxxx
+        0x78, 0x78, 0x78, 0x78,  // xxxx
+        0x78, 0x78, 0x78, 0x78,  // xxxx
+        0x78, 0x78, 0x78, 0x78,  // xxxx
+        0x78, 0x78, 0x78, 0x78,  // xxxx
+        0x78, 0x78, 0x78, 0x78,  // xxxx
+        0x78, 0x78, 0x78, 0x78,  // xxxx
+        0x78, 0x78, 0x78, 0x78,  // xxxx
+        0x78, 0x78, 0x78, 0x78,  // xxxx
+        0x78, 0x78, 0x78, 0x78,  // xxxx
+        0x78, 0x78, 0x78, 0x78,  // xxxx
+        0x78, 0x78, 0x78, 0x78,  // xxxx
+        0x78, 0x78, 0x78, 0x78,  // xxxx
+        0x78, 0x78, 0x78, 0x78,  // xxxx
+        0x78, 0x78, 0x78, 0x78,  // xxxx
+    };
+    const unsigned char kContinuationFrameData[] = {
+        0x00, 0x00, 0x16,        // Length: 22
+        0x09,                    //   Type: CONTINUATION
+        0x04,                    //  Flags: END_HEADERS
+        0x00, 0x00, 0x00, 0x2a,  // Stream: 42
+        0x78, 0x78, 0x78, 0x78,  // xxxx
+        0x78, 0x78, 0x78, 0x78,  // xxxx
+        0x78, 0x78, 0x78, 0x78,  // xxxx
+        0x78, 0x78, 0x78, 0x78,  // xxxx
+        0x78, 0x78, 0x78, 0x78,  // xxxx
+        0x78,                    // x
+    };
+    // frame-format on
+
+    SpdyPushPromiseIR push_promise(/* stream_id = */ 42,
+                                   /* promised_stream_id = */ 57);
+    push_promise.set_padding_len(1);
+    SpdyString big_value(kHttp2MaxControlFrameSendSize, 'x');
+    push_promise.SetHeader("xxx", big_value);
+    SpdySerializedFrame frame(SpdyFramerPeer::SerializePushPromise(
+        &framer, push_promise, use_output_ ? &output_ : nullptr));
+
+    // The entire frame should look like below:
+    // Name                     Length in Byte
+    // ------------------------------------------- Begin of PUSH_PROMISE frame
+    // PUSH_PROMISE header      9
+    // Pad length field         1
+    // Promised stream          4
+    // Length field of key      2
+    // Content of key           3
+    // Length field of value    3
+    // Part of big_value        16361
+    // ------------------------------------------- Begin of CONTINUATION frame
+    // CONTINUATION header      9
+    // Remaining of big_value   22
+    // ------------------------------------------- End
+
+    // Length of everything listed above except big_value.
+    int len_non_data_payload = 31;
+    EXPECT_EQ(kHttp2MaxControlFrameSendSize + len_non_data_payload,
+              frame.size());
+
+    // Partially compare the PUSH_PROMISE frame against the template.
+    const unsigned char* frame_data =
+        reinterpret_cast<const unsigned char*>(frame.data());
+    CompareCharArraysWithHexError(kDescription, frame_data,
+                                  SPDY_ARRAYSIZE(kPartialPushPromiseFrameData),
+                                  kPartialPushPromiseFrameData,
+                                  SPDY_ARRAYSIZE(kPartialPushPromiseFrameData));
+
+    // Compare the CONTINUATION frame against the template.
+    frame_data += kHttp2MaxControlFrameSendSize;
+    CompareCharArraysWithHexError(
+        kDescription, frame_data, SPDY_ARRAYSIZE(kContinuationFrameData),
+        kContinuationFrameData, SPDY_ARRAYSIZE(kContinuationFrameData));
+  }
+}
+
+TEST_P(SpdyFramerTest, CreateAltSvc) {
+  const char kDescription[] = "ALTSVC frame";
+  const unsigned char kType = SerializeFrameType(SpdyFrameType::ALTSVC);
+  const unsigned char kFrameData[] = {
+      0x00, 0x00, 0x49, kType, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x06, 'o',
+      'r',  'i',  'g',  'i',   'n',  'p',  'i',  'd',  '1',  '=',  '"',  'h',
+      'o',  's',  't',  ':',   '4',  '4',  '3',  '"',  ';',  ' ',  'm',  'a',
+      '=',  '5',  ',',  'p',   '%',  '2',  '2',  '%',  '3',  'D',  'i',  '%',
+      '3',  'A',  'd',  '=',   '"',  'h',  '_',  '\\', '\\', 'o',  '\\', '"',
+      's',  't',  ':',  '1',   '2',  '3',  '"',  ';',  ' ',  'm',  'a',  '=',
+      '4',  '2',  ';',  ' ',   'v',  '=',  '"',  '2',  '4',  '"'};
+  SpdyAltSvcIR altsvc_ir(/* stream_id = */ 3);
+  altsvc_ir.set_origin("origin");
+  altsvc_ir.add_altsvc(SpdyAltSvcWireFormat::AlternativeService(
+      "pid1", "host", 443, 5, SpdyAltSvcWireFormat::VersionVector()));
+  altsvc_ir.add_altsvc(SpdyAltSvcWireFormat::AlternativeService(
+      "p\"=i:d", "h_\\o\"st", 123, 42,
+      SpdyAltSvcWireFormat::VersionVector{24}));
+  SpdySerializedFrame frame(framer_.SerializeFrame(altsvc_ir));
+  if (use_output_) {
+    EXPECT_EQ(framer_.SerializeFrame(altsvc_ir, &output_), frame.size());
+    frame = SpdySerializedFrame(output_.Begin(), output_.Size(), false);
+  }
+  CompareFrame(kDescription, frame, kFrameData, SPDY_ARRAYSIZE(kFrameData));
+}
+
+TEST_P(SpdyFramerTest, CreatePriority) {
+  const char kDescription[] = "PRIORITY frame";
+  const unsigned char kFrameData[] = {
+      0x00, 0x00, 0x05,        // Length: 5
+      0x02,                    //   Type: PRIORITY
+      0x00,                    //  Flags: none
+      0x00, 0x00, 0x00, 0x02,  // Stream: 2
+      0x80, 0x00, 0x00, 0x01,  // Parent: 1 (Exclusive)
+      0x10,                    // Weight: 17
+  };
+  SpdyPriorityIR priority_ir(/* stream_id = */ 2,
+                             /* parent_stream_id = */ 1,
+                             /* weight = */ 17,
+                             /* exclusive = */ true);
+  SpdySerializedFrame frame(framer_.SerializeFrame(priority_ir));
+  if (use_output_) {
+    EXPECT_EQ(framer_.SerializeFrame(priority_ir, &output_), frame.size());
+    frame = SpdySerializedFrame(output_.Begin(), output_.Size(), false);
+  }
+  CompareFrame(kDescription, frame, kFrameData, SPDY_ARRAYSIZE(kFrameData));
+}
+
+TEST_P(SpdyFramerTest, CreateUnknown) {
+  const char kDescription[] = "Unknown frame";
+  const uint8_t kType = 0xaf;
+  const uint8_t kFlags = 0x11;
+  const uint8_t kLength = strlen(kDescription);
+  const unsigned char kFrameData[] = {
+      0x00,   0x00, kLength,        // Length: 13
+      kType,                        //   Type: undefined
+      kFlags,                       //  Flags: arbitrary, undefined
+      0x00,   0x00, 0x00,    0x02,  // Stream: 2
+      0x55,   0x6e, 0x6b,    0x6e,  // "Unkn"
+      0x6f,   0x77, 0x6e,    0x20,  // "own "
+      0x66,   0x72, 0x61,    0x6d,  // "fram"
+      0x65,                         // "e"
+  };
+  SpdyUnknownIR unknown_ir(/* stream_id = */ 2,
+                           /* type = */ kType,
+                           /* flags = */ kFlags,
+                           /* payload = */ kDescription);
+  SpdySerializedFrame frame(framer_.SerializeFrame(unknown_ir));
+  if (use_output_) {
+    EXPECT_EQ(framer_.SerializeFrame(unknown_ir, &output_), frame.size());
+    frame = SpdySerializedFrame(output_.Begin(), output_.Size(), false);
+  }
+  CompareFrame(kDescription, frame, kFrameData, SPDY_ARRAYSIZE(kFrameData));
+}
+
+// Test serialization of a SpdyUnknownIR with a defined type, a length field
+// that does not match the payload size and in fact exceeds framer limits, and a
+// stream ID that effectively flips the reserved bit.
+TEST_P(SpdyFramerTest, CreateUnknownUnchecked) {
+  const char kDescription[] = "Unknown frame";
+  const uint8_t kType = 0x00;
+  const uint8_t kFlags = 0x11;
+  const uint8_t kLength = std::numeric_limits<uint8_t>::max();
+  const unsigned int kStreamId = kStreamIdMask + 42;
+  const unsigned char kFrameData[] = {
+      0x00,   0x00, kLength,        // Length: 16426
+      kType,                        //   Type: DATA, defined
+      kFlags,                       //  Flags: arbitrary, undefined
+      0x80,   0x00, 0x00,    0x29,  // Stream: 2147483689
+      0x55,   0x6e, 0x6b,    0x6e,  // "Unkn"
+      0x6f,   0x77, 0x6e,    0x20,  // "own "
+      0x66,   0x72, 0x61,    0x6d,  // "fram"
+      0x65,                         // "e"
+  };
+  TestSpdyUnknownIR unknown_ir(/* stream_id = */ kStreamId,
+                               /* type = */ kType,
+                               /* flags = */ kFlags,
+                               /* payload = */ kDescription);
+  unknown_ir.set_length(kLength);
+  SpdySerializedFrame frame(framer_.SerializeFrame(unknown_ir));
+  if (use_output_) {
+    EXPECT_EQ(framer_.SerializeFrame(unknown_ir, &output_), frame.size());
+    frame = SpdySerializedFrame(output_.Begin(), output_.Size(), false);
+  }
+  CompareFrame(kDescription, frame, kFrameData, SPDY_ARRAYSIZE(kFrameData));
+}
+
+TEST_P(SpdyFramerTest, ReadCompressedHeadersHeaderBlock) {
+  SpdyHeadersIR headers_ir(/* stream_id = */ 1);
+  headers_ir.SetHeader("alpha", "beta");
+  headers_ir.SetHeader("gamma", "delta");
+  SpdySerializedFrame control_frame(SpdyFramerPeer::SerializeHeaders(
+      &framer_, headers_ir, use_output_ ? &output_ : nullptr));
+  TestSpdyVisitor visitor(SpdyFramer::ENABLE_COMPRESSION);
+  visitor.SimulateInFramer(
+      reinterpret_cast<unsigned char*>(control_frame.data()),
+      control_frame.size());
+  EXPECT_EQ(1, visitor.headers_frame_count_);
+  EXPECT_EQ(0, visitor.control_frame_header_data_count_);
+  EXPECT_EQ(0, visitor.zero_length_control_frame_header_data_count_);
+  EXPECT_EQ(0, visitor.end_of_stream_count_);
+  EXPECT_EQ(headers_ir.header_block(), visitor.headers_);
+}
+
+TEST_P(SpdyFramerTest, ReadCompressedHeadersHeaderBlockWithHalfClose) {
+  SpdyHeadersIR headers_ir(/* stream_id = */ 1);
+  headers_ir.set_fin(true);
+  headers_ir.SetHeader("alpha", "beta");
+  headers_ir.SetHeader("gamma", "delta");
+  SpdySerializedFrame control_frame(SpdyFramerPeer::SerializeHeaders(
+      &framer_, headers_ir, use_output_ ? &output_ : nullptr));
+  TestSpdyVisitor visitor(SpdyFramer::ENABLE_COMPRESSION);
+  visitor.SimulateInFramer(
+      reinterpret_cast<unsigned char*>(control_frame.data()),
+      control_frame.size());
+  EXPECT_EQ(1, visitor.headers_frame_count_);
+  EXPECT_EQ(0, visitor.control_frame_header_data_count_);
+  EXPECT_EQ(0, visitor.zero_length_control_frame_header_data_count_);
+  EXPECT_EQ(1, visitor.end_of_stream_count_);
+  EXPECT_EQ(headers_ir.header_block(), visitor.headers_);
+}
+
+TEST_P(SpdyFramerTest, TooLargeHeadersFrameUsesContinuation) {
+  SpdyFramer framer(SpdyFramer::DISABLE_COMPRESSION);
+  SpdyHeadersIR headers(/* stream_id = */ 1);
+  headers.set_padding_len(256);
+
+  // Exact payload length will change with HPACK, but this should be long
+  // enough to cause an overflow.
+  const size_t kBigValueSize = kHttp2MaxControlFrameSendSize;
+  SpdyString big_value(kBigValueSize, 'x');
+  headers.SetHeader("aa", big_value);
+  SpdySerializedFrame control_frame(SpdyFramerPeer::SerializeHeaders(
+      &framer, headers, use_output_ ? &output_ : nullptr));
+  EXPECT_GT(control_frame.size(), kHttp2MaxControlFrameSendSize);
+
+  TestSpdyVisitor visitor(SpdyFramer::DISABLE_COMPRESSION);
+  visitor.SimulateInFramer(
+      reinterpret_cast<unsigned char*>(control_frame.data()),
+      control_frame.size());
+  EXPECT_TRUE(visitor.header_buffer_valid_);
+  EXPECT_EQ(0, visitor.error_count_);
+  EXPECT_EQ(1, visitor.headers_frame_count_);
+  EXPECT_EQ(1, visitor.continuation_count_);
+  EXPECT_EQ(0, visitor.zero_length_control_frame_header_data_count_);
+}
+
+TEST_P(SpdyFramerTest, MultipleContinuationFramesWithIterator) {
+  SpdyFramer framer(SpdyFramer::DISABLE_COMPRESSION);
+  auto headers = SpdyMakeUnique<SpdyHeadersIR>(/* stream_id = */ 1);
+  headers->set_padding_len(256);
+
+  // Exact payload length will change with HPACK, but this should be long
+  // enough to cause an overflow.
+  const size_t kBigValueSize = kHttp2MaxControlFrameSendSize;
+  SpdyString big_valuex(kBigValueSize, 'x');
+  headers->SetHeader("aa", big_valuex);
+  SpdyString big_valuez(kBigValueSize, 'z');
+  headers->SetHeader("bb", big_valuez);
+
+  SpdyFramer::SpdyHeaderFrameIterator frame_it(&framer, std::move(headers));
+
+  EXPECT_TRUE(frame_it.HasNextFrame());
+  EXPECT_GT(frame_it.NextFrame(&output_), 0u);
+  SpdySerializedFrame headers_frame(output_.Begin(), output_.Size(), false);
+  EXPECT_EQ(headers_frame.size(), kHttp2MaxControlFrameSendSize);
+
+  TestSpdyVisitor visitor(SpdyFramer::DISABLE_COMPRESSION);
+  visitor.SimulateInFramer(
+      reinterpret_cast<unsigned char*>(headers_frame.data()),
+      headers_frame.size());
+  EXPECT_TRUE(visitor.header_buffer_valid_);
+  EXPECT_EQ(0, visitor.error_count_);
+  EXPECT_EQ(1, visitor.headers_frame_count_);
+  EXPECT_EQ(0, visitor.continuation_count_);
+  EXPECT_EQ(0, visitor.zero_length_control_frame_header_data_count_);
+
+  output_.Reset();
+  EXPECT_TRUE(frame_it.HasNextFrame());
+  EXPECT_GT(frame_it.NextFrame(&output_), 0u);
+  SpdySerializedFrame first_cont_frame(output_.Begin(), output_.Size(), false);
+  EXPECT_EQ(first_cont_frame.size(), kHttp2MaxControlFrameSendSize);
+
+  visitor.SimulateInFramer(
+      reinterpret_cast<unsigned char*>(first_cont_frame.data()),
+      first_cont_frame.size());
+  EXPECT_TRUE(visitor.header_buffer_valid_);
+  EXPECT_EQ(0, visitor.error_count_);
+  EXPECT_EQ(1, visitor.headers_frame_count_);
+  EXPECT_EQ(1, visitor.continuation_count_);
+  EXPECT_EQ(0, visitor.zero_length_control_frame_header_data_count_);
+
+  output_.Reset();
+  EXPECT_TRUE(frame_it.HasNextFrame());
+  EXPECT_GT(frame_it.NextFrame(&output_), 0u);
+  SpdySerializedFrame second_cont_frame(output_.Begin(), output_.Size(), false);
+  EXPECT_LT(second_cont_frame.size(), kHttp2MaxControlFrameSendSize);
+
+  visitor.SimulateInFramer(
+      reinterpret_cast<unsigned char*>(second_cont_frame.data()),
+      second_cont_frame.size());
+  EXPECT_TRUE(visitor.header_buffer_valid_);
+  EXPECT_EQ(0, visitor.error_count_);
+  EXPECT_EQ(1, visitor.headers_frame_count_);
+  EXPECT_EQ(2, visitor.continuation_count_);
+  EXPECT_EQ(0, visitor.zero_length_control_frame_header_data_count_);
+
+  EXPECT_FALSE(frame_it.HasNextFrame());
+}
+
+TEST_P(SpdyFramerTest, PushPromiseFramesWithIterator) {
+  SpdyFramer framer(SpdyFramer::DISABLE_COMPRESSION);
+  auto push_promise =
+      SpdyMakeUnique<SpdyPushPromiseIR>(/* stream_id = */ 1,
+                                        /* promised_stream_id = */ 2);
+  push_promise->set_padding_len(256);
+
+  // Exact payload length will change with HPACK, but this should be long
+  // enough to cause an overflow.
+  const size_t kBigValueSize = kHttp2MaxControlFrameSendSize;
+  SpdyString big_valuex(kBigValueSize, 'x');
+  push_promise->SetHeader("aa", big_valuex);
+  SpdyString big_valuez(kBigValueSize, 'z');
+  push_promise->SetHeader("bb", big_valuez);
+
+  SpdyFramer::SpdyPushPromiseFrameIterator frame_it(&framer,
+                                                    std::move(push_promise));
+
+  EXPECT_TRUE(frame_it.HasNextFrame());
+  EXPECT_GT(frame_it.NextFrame(&output_), 0u);
+  SpdySerializedFrame push_promise_frame(output_.Begin(), output_.Size(),
+                                         false);
+  EXPECT_EQ(push_promise_frame.size(), kHttp2MaxControlFrameSendSize);
+
+  TestSpdyVisitor visitor(SpdyFramer::DISABLE_COMPRESSION);
+  visitor.SimulateInFramer(
+      reinterpret_cast<unsigned char*>(push_promise_frame.data()),
+      push_promise_frame.size());
+  EXPECT_TRUE(visitor.header_buffer_valid_);
+  EXPECT_EQ(0, visitor.error_count_);
+  EXPECT_EQ(1, visitor.push_promise_frame_count_);
+  EXPECT_EQ(0, visitor.continuation_count_);
+  EXPECT_EQ(0, visitor.zero_length_control_frame_header_data_count_);
+
+  EXPECT_TRUE(frame_it.HasNextFrame());
+  output_.Reset();
+  EXPECT_GT(frame_it.NextFrame(&output_), 0u);
+  SpdySerializedFrame first_cont_frame(output_.Begin(), output_.Size(), false);
+
+  EXPECT_EQ(first_cont_frame.size(), kHttp2MaxControlFrameSendSize);
+  visitor.SimulateInFramer(
+      reinterpret_cast<unsigned char*>(first_cont_frame.data()),
+      first_cont_frame.size());
+  EXPECT_TRUE(visitor.header_buffer_valid_);
+  EXPECT_EQ(0, visitor.error_count_);
+  EXPECT_EQ(1, visitor.push_promise_frame_count_);
+  EXPECT_EQ(1, visitor.continuation_count_);
+  EXPECT_EQ(0, visitor.zero_length_control_frame_header_data_count_);
+
+  EXPECT_TRUE(frame_it.HasNextFrame());
+  output_.Reset();
+  EXPECT_GT(frame_it.NextFrame(&output_), 0u);
+  SpdySerializedFrame second_cont_frame(output_.Begin(), output_.Size(), false);
+  EXPECT_LT(second_cont_frame.size(), kHttp2MaxControlFrameSendSize);
+
+  visitor.SimulateInFramer(
+      reinterpret_cast<unsigned char*>(second_cont_frame.data()),
+      second_cont_frame.size());
+  EXPECT_TRUE(visitor.header_buffer_valid_);
+  EXPECT_EQ(0, visitor.error_count_);
+  EXPECT_EQ(1, visitor.push_promise_frame_count_);
+  EXPECT_EQ(2, visitor.continuation_count_);
+  EXPECT_EQ(0, visitor.zero_length_control_frame_header_data_count_);
+
+  EXPECT_FALSE(frame_it.HasNextFrame());
+}
+
+class SpdyControlFrameIteratorTest : public ::testing::Test {
+ public:
+  SpdyControlFrameIteratorTest() : output_(output_buffer, kSize) {}
+
+  void RunTest(std::unique_ptr<SpdyFrameIR> ir) {
+    SpdyFramer framer(SpdyFramer::DISABLE_COMPRESSION);
+    SpdySerializedFrame frame(framer.SerializeFrame(*ir));
+    std::unique_ptr<SpdyFrameSequence> it =
+        SpdyFramer::CreateIterator(&framer, std::move(ir));
+    EXPECT_TRUE(it->HasNextFrame());
+    EXPECT_EQ(it->NextFrame(&output_), frame.size());
+    EXPECT_FALSE(it->HasNextFrame());
+  }
+
+ private:
+  ArrayOutputBuffer output_;
+};
+
+TEST_F(SpdyControlFrameIteratorTest, RstStreamFrameWithIterator) {
+  auto ir = SpdyMakeUnique<SpdyRstStreamIR>(0, ERROR_CODE_PROTOCOL_ERROR);
+  RunTest(std::move(ir));
+}
+
+TEST_F(SpdyControlFrameIteratorTest, SettingsFrameWithIterator) {
+  auto ir = SpdyMakeUnique<SpdySettingsIR>();
+  uint32_t kValue = 0x0a0b0c0d;
+  SpdyKnownSettingsId kId = SETTINGS_INITIAL_WINDOW_SIZE;
+  ir->AddSetting(kId, kValue);
+  RunTest(std::move(ir));
+}
+
+TEST_F(SpdyControlFrameIteratorTest, PingFrameWithIterator) {
+  const SpdyPingId kPingId = 0x123456789abcdeffULL;
+  auto ir = SpdyMakeUnique<SpdyPingIR>(kPingId);
+  RunTest(std::move(ir));
+}
+
+TEST_F(SpdyControlFrameIteratorTest, GoAwayFrameWithIterator) {
+  auto ir = SpdyMakeUnique<SpdyGoAwayIR>(0, ERROR_CODE_NO_ERROR, "GA");
+  RunTest(std::move(ir));
+}
+
+TEST_F(SpdyControlFrameIteratorTest, WindowUpdateFrameWithIterator) {
+  auto ir = SpdyMakeUnique<SpdyWindowUpdateIR>(1, 1);
+  RunTest(std::move(ir));
+}
+
+TEST_F(SpdyControlFrameIteratorTest, AtlSvcFrameWithIterator) {
+  auto ir = SpdyMakeUnique<SpdyAltSvcIR>(3);
+  ir->set_origin("origin");
+  ir->add_altsvc(SpdyAltSvcWireFormat::AlternativeService(
+      "pid1", "host", 443, 5, SpdyAltSvcWireFormat::VersionVector()));
+  ir->add_altsvc(SpdyAltSvcWireFormat::AlternativeService(
+      "p\"=i:d", "h_\\o\"st", 123, 42,
+      SpdyAltSvcWireFormat::VersionVector{24}));
+  RunTest(std::move(ir));
+}
+
+TEST_F(SpdyControlFrameIteratorTest, PriorityFrameWithIterator) {
+  auto ir = SpdyMakeUnique<SpdyPriorityIR>(2, 1, 17, true);
+  RunTest(std::move(ir));
+}
+
+TEST_P(SpdyFramerTest, TooLargePushPromiseFrameUsesContinuation) {
+  SpdyFramer framer(SpdyFramer::DISABLE_COMPRESSION);
+  SpdyPushPromiseIR push_promise(/* stream_id = */ 1,
+                                 /* promised_stream_id = */ 2);
+  push_promise.set_padding_len(256);
+
+  // Exact payload length will change with HPACK, but this should be long
+  // enough to cause an overflow.
+  const size_t kBigValueSize = kHttp2MaxControlFrameSendSize;
+  SpdyString big_value(kBigValueSize, 'x');
+  push_promise.SetHeader("aa", big_value);
+  SpdySerializedFrame control_frame(SpdyFramerPeer::SerializePushPromise(
+      &framer, push_promise, use_output_ ? &output_ : nullptr));
+  EXPECT_GT(control_frame.size(), kHttp2MaxControlFrameSendSize);
+
+  TestSpdyVisitor visitor(SpdyFramer::DISABLE_COMPRESSION);
+  visitor.SimulateInFramer(
+      reinterpret_cast<unsigned char*>(control_frame.data()),
+      control_frame.size());
+  EXPECT_TRUE(visitor.header_buffer_valid_);
+  EXPECT_EQ(0, visitor.error_count_);
+  EXPECT_EQ(1, visitor.push_promise_frame_count_);
+  EXPECT_EQ(1, visitor.continuation_count_);
+  EXPECT_EQ(0, visitor.zero_length_control_frame_header_data_count_);
+}
+
+// Check that the framer stops delivering header data chunks once the visitor
+// declares it doesn't want any more. This is important to guard against
+// "zip bomb" types of attacks.
+TEST_P(SpdyFramerTest, ControlFrameMuchTooLarge) {
+  const size_t kHeaderBufferChunks = 4;
+  const size_t kHeaderBufferSize =
+      kHttp2DefaultFramePayloadLimit / kHeaderBufferChunks;
+  const size_t kBigValueSize = kHeaderBufferSize * 2;
+  SpdyString big_value(kBigValueSize, 'x');
+  SpdyHeadersIR headers(/* stream_id = */ 1);
+  headers.set_fin(true);
+  headers.SetHeader("aa", big_value);
+  SpdySerializedFrame control_frame(SpdyFramerPeer::SerializeHeaders(
+      &framer_, headers, use_output_ ? &output_ : nullptr));
+  TestSpdyVisitor visitor(SpdyFramer::ENABLE_COMPRESSION);
+  visitor.set_header_buffer_size(kHeaderBufferSize);
+  visitor.SimulateInFramer(
+      reinterpret_cast<unsigned char*>(control_frame.data()),
+      control_frame.size());
+  // It's up to the visitor to ignore extraneous header data; the framer
+  // won't throw an error.
+  EXPECT_GT(visitor.header_bytes_received_, visitor.header_buffer_size_);
+  EXPECT_EQ(1, visitor.end_of_stream_count_);
+}
+
+TEST_P(SpdyFramerTest, ControlFrameSizesAreValidated) {
+  // Create a GoAway frame that has a few extra bytes at the end.
+  const size_t length = 20;
+
+  // HTTP/2 GOAWAY frames are only bound by a minimal length, since they may
+  // carry opaque data. Verify that minimal length is tested.
+  ASSERT_GT(kGoawayFrameMinimumSize, kFrameHeaderSize);
+  const size_t less_than_min_length =
+      kGoawayFrameMinimumSize - kFrameHeaderSize - 1;
+  ASSERT_LE(less_than_min_length, std::numeric_limits<unsigned char>::max());
+  const unsigned char kH2Len = static_cast<unsigned char>(less_than_min_length);
+  const unsigned char kH2FrameData[] = {
+      0x00, 0x00, kH2Len,        // Length: min length - 1
+      0x07,                      //   Type: GOAWAY
+      0x00,                      //  Flags: none
+      0x00, 0x00, 0x00,   0x00,  // Stream: 0
+      0x00, 0x00, 0x00,   0x00,  //   Last: 0
+      0x00, 0x00, 0x00,          // Truncated Status Field
+  };
+  const size_t pad_length = length + kFrameHeaderSize - sizeof(kH2FrameData);
+  SpdyString pad(pad_length, 'A');
+  TestSpdyVisitor visitor(SpdyFramer::DISABLE_COMPRESSION);
+
+  visitor.SimulateInFramer(kH2FrameData, sizeof(kH2FrameData));
+  visitor.SimulateInFramer(reinterpret_cast<const unsigned char*>(pad.c_str()),
+                           pad.length());
+
+  EXPECT_EQ(1, visitor.error_count_);  // This generated an error.
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_INVALID_CONTROL_FRAME,
+            visitor.deframer_.spdy_framer_error())
+      << Http2DecoderAdapter::SpdyFramerErrorToString(
+             visitor.deframer_.spdy_framer_error());
+  EXPECT_EQ(0, visitor.goaway_count_);  // Frame not parsed.
+}
+
+TEST_P(SpdyFramerTest, ReadZeroLenSettingsFrame) {
+  SpdySettingsIR settings_ir;
+  SpdySerializedFrame control_frame(framer_.SerializeSettings(settings_ir));
+  if (use_output_) {
+    ASSERT_TRUE(framer_.SerializeSettings(settings_ir, &output_));
+    control_frame = SpdySerializedFrame(output_.Begin(), output_.Size(), false);
+  }
+  SetFrameLength(&control_frame, 0);
+  TestSpdyVisitor visitor(SpdyFramer::DISABLE_COMPRESSION);
+  visitor.SimulateInFramer(
+      reinterpret_cast<unsigned char*>(control_frame.data()), kFrameHeaderSize);
+  // Zero-len settings frames are permitted as of HTTP/2.
+  EXPECT_EQ(0, visitor.error_count_);
+}
+
+// Tests handling of SETTINGS frames with invalid length.
+TEST_P(SpdyFramerTest, ReadBogusLenSettingsFrame) {
+  SpdySettingsIR settings_ir;
+
+  // Add settings to more than fill the frame so that we don't get a buffer
+  // overflow when calling SimulateInFramer() below. These settings must be
+  // distinct parameters because SpdySettingsIR has a map for settings, and
+  // will collapse multiple copies of the same parameter.
+  settings_ir.AddSetting(SETTINGS_INITIAL_WINDOW_SIZE, 0x00000002);
+  settings_ir.AddSetting(SETTINGS_MAX_CONCURRENT_STREAMS, 0x00000002);
+  SpdySerializedFrame control_frame(framer_.SerializeSettings(settings_ir));
+  if (use_output_) {
+    ASSERT_TRUE(framer_.SerializeSettings(settings_ir, &output_));
+    control_frame = SpdySerializedFrame(output_.Begin(), output_.Size(), false);
+  }
+  const size_t kNewLength = 8;
+  SetFrameLength(&control_frame, kNewLength);
+  TestSpdyVisitor visitor(SpdyFramer::DISABLE_COMPRESSION);
+  visitor.SimulateInFramer(
+      reinterpret_cast<unsigned char*>(control_frame.data()),
+      kFrameHeaderSize + kNewLength);
+  // Should generate an error, since its not possible to have a
+  // settings frame of length kNewLength.
+  EXPECT_EQ(1, visitor.error_count_);
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_INVALID_CONTROL_FRAME_SIZE,
+            visitor.deframer_.spdy_framer_error())
+      << Http2DecoderAdapter::SpdyFramerErrorToString(
+             visitor.deframer_.spdy_framer_error());
+}
+
+// Tests handling of larger SETTINGS frames.
+TEST_P(SpdyFramerTest, ReadLargeSettingsFrame) {
+  SpdySettingsIR settings_ir;
+  settings_ir.AddSetting(SETTINGS_HEADER_TABLE_SIZE, 5);
+  settings_ir.AddSetting(SETTINGS_ENABLE_PUSH, 6);
+  settings_ir.AddSetting(SETTINGS_MAX_CONCURRENT_STREAMS, 7);
+
+  SpdySerializedFrame control_frame(framer_.SerializeSettings(settings_ir));
+  if (use_output_) {
+    ASSERT_TRUE(framer_.SerializeSettings(settings_ir, &output_));
+    control_frame = SpdySerializedFrame(output_.Begin(), output_.Size(), false);
+  }
+
+  TestSpdyVisitor visitor(SpdyFramer::DISABLE_COMPRESSION);
+
+  // Read all at once.
+  visitor.SimulateInFramer(
+      reinterpret_cast<unsigned char*>(control_frame.data()),
+      control_frame.size());
+  EXPECT_EQ(0, visitor.error_count_);
+  EXPECT_EQ(3, visitor.setting_count_);
+  EXPECT_EQ(1, visitor.settings_ack_sent_);
+
+  // Read data in small chunks.
+  size_t framed_data = 0;
+  size_t unframed_data = control_frame.size();
+  size_t kReadChunkSize = 5;  // Read five bytes at a time.
+  while (unframed_data > 0) {
+    size_t to_read = std::min(kReadChunkSize, unframed_data);
+    visitor.SimulateInFramer(
+        reinterpret_cast<unsigned char*>(control_frame.data() + framed_data),
+        to_read);
+    unframed_data -= to_read;
+    framed_data += to_read;
+  }
+  EXPECT_EQ(0, visitor.error_count_);
+  EXPECT_EQ(3 * 2, visitor.setting_count_);
+  EXPECT_EQ(2, visitor.settings_ack_sent_);
+}
+
+// Tests handling of SETTINGS frame with duplicate entries.
+TEST_P(SpdyFramerTest, ReadDuplicateSettings) {
+  const unsigned char kH2FrameData[] = {
+      0x00, 0x00, 0x12,        // Length: 18
+      0x04,                    //   Type: SETTINGS
+      0x00,                    //  Flags: none
+      0x00, 0x00, 0x00, 0x00,  // Stream: 0
+      0x00, 0x01,              //  Param: HEADER_TABLE_SIZE
+      0x00, 0x00, 0x00, 0x02,  //  Value: 2
+      0x00, 0x01,              //  Param: HEADER_TABLE_SIZE
+      0x00, 0x00, 0x00, 0x03,  //  Value: 3
+      0x00, 0x03,              //  Param: MAX_CONCURRENT_STREAMS
+      0x00, 0x00, 0x00, 0x03,  //  Value: 3
+  };
+
+  TestSpdyVisitor visitor(SpdyFramer::DISABLE_COMPRESSION);
+  visitor.SimulateInFramer(kH2FrameData, sizeof(kH2FrameData));
+
+  // In HTTP/2, duplicate settings are allowed;
+  // each setting replaces the previous value for that setting.
+  EXPECT_EQ(3, visitor.setting_count_);
+  EXPECT_EQ(0, visitor.error_count_);
+  EXPECT_EQ(1, visitor.settings_ack_sent_);
+}
+
+// Tests handling of SETTINGS frame with a setting we don't recognize.
+TEST_P(SpdyFramerTest, ReadUnknownSettingsId) {
+  const unsigned char kH2FrameData[] = {
+      0x00, 0x00, 0x06,        // Length: 6
+      0x04,                    //   Type: SETTINGS
+      0x00,                    //  Flags: none
+      0x00, 0x00, 0x00, 0x00,  // Stream: 0
+      0x00, 0x10,              //  Param: 16
+      0x00, 0x00, 0x00, 0x02,  //  Value: 2
+  };
+
+  TestSpdyVisitor visitor(SpdyFramer::DISABLE_COMPRESSION);
+  visitor.SimulateInFramer(kH2FrameData, sizeof(kH2FrameData));
+
+  // In HTTP/2, we ignore unknown settings because of extensions. However, we
+  // pass the SETTINGS to the visitor, which can decide how to handle them.
+  EXPECT_EQ(1, visitor.setting_count_);
+  EXPECT_EQ(0, visitor.error_count_);
+}
+
+TEST_P(SpdyFramerTest, ReadKnownAndUnknownSettingsWithExtension) {
+  const unsigned char kH2FrameData[] = {
+      0x00, 0x00, 0x12,        // Length: 18
+      0x04,                    //   Type: SETTINGS
+      0x00,                    //  Flags: none
+      0x00, 0x00, 0x00, 0x00,  // Stream: 0
+      0x00, 0x10,              //  Param: 16
+      0x00, 0x00, 0x00, 0x02,  //  Value: 2
+      0x00, 0x5f,              //  Param: 95
+      0x00, 0x01, 0x00, 0x02,  //  Value: 65538
+      0x00, 0x02,              //  Param: ENABLE_PUSH
+      0x00, 0x00, 0x00, 0x01,  //  Value: 1
+  };
+
+  TestSpdyVisitor visitor(SpdyFramer::DISABLE_COMPRESSION);
+  TestExtension extension;
+  visitor.set_extension_visitor(&extension);
+  visitor.SimulateInFramer(kH2FrameData, sizeof(kH2FrameData));
+
+  // In HTTP/2, we ignore unknown settings because of extensions. However, we
+  // pass the SETTINGS to the visitor, which can decide how to handle them.
+  EXPECT_EQ(3, visitor.setting_count_);
+  EXPECT_EQ(0, visitor.error_count_);
+
+  // The extension receives all SETTINGS, including the non-standard SETTINGS.
+  EXPECT_THAT(
+      extension.settings_received_,
+      testing::ElementsAre(testing::Pair(16, 2), testing::Pair(95, 65538),
+                           testing::Pair(2, 1)));
+}
+
+// Tests handling of SETTINGS frame with entries out of order.
+TEST_P(SpdyFramerTest, ReadOutOfOrderSettings) {
+  const unsigned char kH2FrameData[] = {
+      0x00, 0x00, 0x12,        // Length: 18
+      0x04,                    //   Type: SETTINGS
+      0x00,                    //  Flags: none
+      0x00, 0x00, 0x00, 0x00,  // Stream: 0
+      0x00, 0x02,              //  Param: ENABLE_PUSH
+      0x00, 0x00, 0x00, 0x02,  //  Value: 2
+      0x00, 0x01,              //  Param: HEADER_TABLE_SIZE
+      0x00, 0x00, 0x00, 0x03,  //  Value: 3
+      0x00, 0x03,              //  Param: MAX_CONCURRENT_STREAMS
+      0x00, 0x00, 0x00, 0x03,  //  Value: 3
+  };
+
+  TestSpdyVisitor visitor(SpdyFramer::DISABLE_COMPRESSION);
+  visitor.SimulateInFramer(kH2FrameData, sizeof(kH2FrameData));
+
+  // In HTTP/2, settings are allowed in any order.
+  EXPECT_EQ(3, visitor.setting_count_);
+  EXPECT_EQ(0, visitor.error_count_);
+}
+
+TEST_P(SpdyFramerTest, ProcessSettingsAckFrame) {
+  const unsigned char kFrameData[] = {
+      0x00, 0x00, 0x00,        // Length: 0
+      0x04,                    //   Type: SETTINGS
+      0x01,                    //  Flags: ACK
+      0x00, 0x00, 0x00, 0x00,  // Stream: 0
+  };
+
+  TestSpdyVisitor visitor(SpdyFramer::DISABLE_COMPRESSION);
+  visitor.SimulateInFramer(kFrameData, sizeof(kFrameData));
+
+  EXPECT_EQ(0, visitor.error_count_);
+  EXPECT_EQ(0, visitor.setting_count_);
+  EXPECT_EQ(1, visitor.settings_ack_received_);
+}
+
+TEST_P(SpdyFramerTest, ProcessDataFrameWithPadding) {
+  const int kPaddingLen = 119;
+  const char data_payload[] = "hello";
+
+  testing::StrictMock<test::MockSpdyFramerVisitor> visitor;
+  deframer_.set_visitor(&visitor);
+
+  SpdyDataIR data_ir(/* stream_id = */ 1, data_payload);
+  data_ir.set_padding_len(kPaddingLen);
+  SpdySerializedFrame frame(framer_.SerializeData(data_ir));
+
+  int bytes_consumed = 0;
+
+  // Send the frame header.
+  EXPECT_CALL(visitor,
+              OnDataFrameHeader(1, kPaddingLen + strlen(data_payload), false));
+  CHECK_EQ(kDataFrameMinimumSize,
+           deframer_.ProcessInput(frame.data(), kDataFrameMinimumSize));
+  CHECK_EQ(deframer_.state(),
+           Http2DecoderAdapter::SPDY_READ_DATA_FRAME_PADDING_LENGTH);
+  CHECK_EQ(deframer_.spdy_framer_error(), Http2DecoderAdapter::SPDY_NO_ERROR);
+  bytes_consumed += kDataFrameMinimumSize;
+
+  // Send the padding length field.
+  EXPECT_CALL(visitor, OnStreamPadLength(1, kPaddingLen - 1));
+  CHECK_EQ(1u, deframer_.ProcessInput(frame.data() + bytes_consumed, 1));
+  CHECK_EQ(deframer_.state(), Http2DecoderAdapter::SPDY_FORWARD_STREAM_FRAME);
+  CHECK_EQ(deframer_.spdy_framer_error(), Http2DecoderAdapter::SPDY_NO_ERROR);
+  bytes_consumed += 1;
+
+  // Send the first two bytes of the data payload, i.e., "he".
+  EXPECT_CALL(visitor, OnStreamFrameData(1, _, 2));
+  CHECK_EQ(2u, deframer_.ProcessInput(frame.data() + bytes_consumed, 2));
+  CHECK_EQ(deframer_.state(), Http2DecoderAdapter::SPDY_FORWARD_STREAM_FRAME);
+  CHECK_EQ(deframer_.spdy_framer_error(), Http2DecoderAdapter::SPDY_NO_ERROR);
+  bytes_consumed += 2;
+
+  // Send the rest three bytes of the data payload, i.e., "llo".
+  EXPECT_CALL(visitor, OnStreamFrameData(1, _, 3));
+  CHECK_EQ(3u, deframer_.ProcessInput(frame.data() + bytes_consumed, 3));
+  CHECK_EQ(deframer_.state(), Http2DecoderAdapter::SPDY_CONSUME_PADDING);
+  CHECK_EQ(deframer_.spdy_framer_error(), Http2DecoderAdapter::SPDY_NO_ERROR);
+  bytes_consumed += 3;
+
+  // Send the first 100 bytes of the padding payload.
+  EXPECT_CALL(visitor, OnStreamPadding(1, 100));
+  CHECK_EQ(100u, deframer_.ProcessInput(frame.data() + bytes_consumed, 100));
+  CHECK_EQ(deframer_.state(), Http2DecoderAdapter::SPDY_CONSUME_PADDING);
+  CHECK_EQ(deframer_.spdy_framer_error(), Http2DecoderAdapter::SPDY_NO_ERROR);
+  bytes_consumed += 100;
+
+  // Send rest of the padding payload.
+  EXPECT_CALL(visitor, OnStreamPadding(1, 18));
+  CHECK_EQ(18u, deframer_.ProcessInput(frame.data() + bytes_consumed, 18));
+  CHECK_EQ(deframer_.state(), Http2DecoderAdapter::SPDY_READY_FOR_FRAME);
+  CHECK_EQ(deframer_.spdy_framer_error(), Http2DecoderAdapter::SPDY_NO_ERROR);
+}
+
+TEST_P(SpdyFramerTest, ReadWindowUpdate) {
+  SpdySerializedFrame control_frame(framer_.SerializeWindowUpdate(
+      SpdyWindowUpdateIR(/* stream_id = */ 1, /* delta = */ 2)));
+  if (use_output_) {
+    ASSERT_TRUE(framer_.SerializeWindowUpdate(
+        SpdyWindowUpdateIR(/* stream_id = */ 1, /* delta = */ 2), &output_));
+    control_frame = SpdySerializedFrame(output_.Begin(), output_.Size(), false);
+  }
+  TestSpdyVisitor visitor(SpdyFramer::DISABLE_COMPRESSION);
+  visitor.SimulateInFramer(
+      reinterpret_cast<unsigned char*>(control_frame.data()),
+      control_frame.size());
+  EXPECT_EQ(1u, visitor.last_window_update_stream_);
+  EXPECT_EQ(2, visitor.last_window_update_delta_);
+}
+
+TEST_P(SpdyFramerTest, ReadCompressedPushPromise) {
+  SpdyPushPromiseIR push_promise(/* stream_id = */ 42,
+                                 /* promised_stream_id = */ 57);
+  push_promise.SetHeader("foo", "bar");
+  push_promise.SetHeader("bar", "foofoo");
+  SpdySerializedFrame frame(SpdyFramerPeer::SerializePushPromise(
+      &framer_, push_promise, use_output_ ? &output_ : nullptr));
+  TestSpdyVisitor visitor(SpdyFramer::ENABLE_COMPRESSION);
+  visitor.SimulateInFramer(reinterpret_cast<unsigned char*>(frame.data()),
+                           frame.size());
+  EXPECT_EQ(42u, visitor.last_push_promise_stream_);
+  EXPECT_EQ(57u, visitor.last_push_promise_promised_stream_);
+  EXPECT_EQ(push_promise.header_block(), visitor.headers_);
+}
+
+TEST_P(SpdyFramerTest, ReadHeadersWithContinuation) {
+  // frame-format off
+  const unsigned char kInput[] = {
+      0x00, 0x00, 0x14,                       // Length: 20
+      0x01,                                   //   Type: HEADERS
+      0x08,                                   //  Flags: PADDED
+      0x00, 0x00, 0x00, 0x01,                 // Stream: 1
+      0x03,                                   // PadLen: 3 trailing bytes
+      0x00,                                   // Unindexed Entry
+      0x06,                                   // Name Len: 6
+      'c',  'o',  'o',  'k',  'i', 'e',       // Name
+      0x07,                                   // Value Len: 7
+      'f',  'o',  'o',  '=',  'b', 'a', 'r',  // Value
+      0x00, 0x00, 0x00,                       // Padding
+
+      0x00, 0x00, 0x14,                            // Length: 20
+      0x09,                                        //   Type: CONTINUATION
+      0x00,                                        //  Flags: none
+      0x00, 0x00, 0x00, 0x01,                      // Stream: 1
+      0x00,                                        // Unindexed Entry
+      0x06,                                        // Name Len: 6
+      'c',  'o',  'o',  'k',  'i', 'e',            // Name
+      0x08,                                        // Value Len: 7
+      'b',  'a',  'z',  '=',  'b', 'i', 'n', 'g',  // Value
+      0x00,                                        // Unindexed Entry
+      0x06,                                        // Name Len: 6
+      'c',                                         // Name (split)
+
+      0x00, 0x00, 0x12,             // Length: 18
+      0x09,                         //   Type: CONTINUATION
+      0x04,                         //  Flags: END_HEADERS
+      0x00, 0x00, 0x00, 0x01,       // Stream: 1
+      'o',  'o',  'k',  'i',  'e',  // Name (continued)
+      0x00,                         // Value Len: 0
+      0x00,                         // Unindexed Entry
+      0x04,                         // Name Len: 4
+      'n',  'a',  'm',  'e',        // Name
+      0x05,                         // Value Len: 5
+      'v',  'a',  'l',  'u',  'e',  // Value
+  };
+  // frame-format on
+
+  TestSpdyVisitor visitor(SpdyFramer::DISABLE_COMPRESSION);
+  visitor.SimulateInFramer(kInput, sizeof(kInput));
+
+  EXPECT_EQ(0, visitor.error_count_);
+  EXPECT_EQ(1, visitor.headers_frame_count_);
+  EXPECT_EQ(2, visitor.continuation_count_);
+  EXPECT_EQ(0, visitor.zero_length_control_frame_header_data_count_);
+  EXPECT_EQ(0, visitor.end_of_stream_count_);
+
+  EXPECT_THAT(
+      visitor.headers_,
+      testing::ElementsAre(testing::Pair("cookie", "foo=bar; baz=bing; "),
+                           testing::Pair("name", "value")));
+}
+
+TEST_P(SpdyFramerTest, ReadHeadersWithContinuationAndFin) {
+  // frame-format off
+  const unsigned char kInput[] = {
+      0x00, 0x00, 0x10,                       // Length: 20
+      0x01,                                   //   Type: HEADERS
+      0x01,                                   //  Flags: END_STREAM
+      0x00, 0x00, 0x00, 0x01,                 // Stream: 1
+      0x00,                                   // Unindexed Entry
+      0x06,                                   // Name Len: 6
+      'c',  'o',  'o',  'k',  'i', 'e',       // Name
+      0x07,                                   // Value Len: 7
+      'f',  'o',  'o',  '=',  'b', 'a', 'r',  // Value
+
+      0x00, 0x00, 0x14,                            // Length: 20
+      0x09,                                        //   Type: CONTINUATION
+      0x00,                                        //  Flags: none
+      0x00, 0x00, 0x00, 0x01,                      // Stream: 1
+      0x00,                                        // Unindexed Entry
+      0x06,                                        // Name Len: 6
+      'c',  'o',  'o',  'k',  'i', 'e',            // Name
+      0x08,                                        // Value Len: 7
+      'b',  'a',  'z',  '=',  'b', 'i', 'n', 'g',  // Value
+      0x00,                                        // Unindexed Entry
+      0x06,                                        // Name Len: 6
+      'c',                                         // Name (split)
+
+      0x00, 0x00, 0x12,             // Length: 18
+      0x09,                         //   Type: CONTINUATION
+      0x04,                         //  Flags: END_HEADERS
+      0x00, 0x00, 0x00, 0x01,       // Stream: 1
+      'o',  'o',  'k',  'i',  'e',  // Name (continued)
+      0x00,                         // Value Len: 0
+      0x00,                         // Unindexed Entry
+      0x04,                         // Name Len: 4
+      'n',  'a',  'm',  'e',        // Name
+      0x05,                         // Value Len: 5
+      'v',  'a',  'l',  'u',  'e',  // Value
+  };
+  // frame-format on
+
+  TestSpdyVisitor visitor(SpdyFramer::DISABLE_COMPRESSION);
+  visitor.SimulateInFramer(kInput, sizeof(kInput));
+
+  EXPECT_EQ(0, visitor.error_count_);
+  EXPECT_EQ(1, visitor.headers_frame_count_);
+  EXPECT_EQ(2, visitor.continuation_count_);
+  EXPECT_EQ(1, visitor.fin_flag_count_);
+  EXPECT_EQ(0, visitor.zero_length_control_frame_header_data_count_);
+  EXPECT_EQ(1, visitor.end_of_stream_count_);
+
+  EXPECT_THAT(
+      visitor.headers_,
+      testing::ElementsAre(testing::Pair("cookie", "foo=bar; baz=bing; "),
+                           testing::Pair("name", "value")));
+}
+
+TEST_P(SpdyFramerTest, ReadPushPromiseWithContinuation) {
+  // frame-format off
+  const unsigned char kInput[] = {
+      0x00, 0x00, 0x17,                       // Length: 23
+      0x05,                                   //   Type: PUSH_PROMISE
+      0x08,                                   //  Flags: PADDED
+      0x00, 0x00, 0x00, 0x01,                 // Stream: 1
+      0x02,                                   // PadLen: 2 trailing bytes
+      0x00, 0x00, 0x00, 0x2a,                 // Promise: 42
+      0x00,                                   // Unindexed Entry
+      0x06,                                   // Name Len: 6
+      'c',  'o',  'o',  'k',  'i', 'e',       // Name
+      0x07,                                   // Value Len: 7
+      'f',  'o',  'o',  '=',  'b', 'a', 'r',  // Value
+      0x00, 0x00,                             // Padding
+
+      0x00, 0x00, 0x14,                            // Length: 20
+      0x09,                                        //   Type: CONTINUATION
+      0x00,                                        //  Flags: none
+      0x00, 0x00, 0x00, 0x01,                      // Stream: 1
+      0x00,                                        // Unindexed Entry
+      0x06,                                        // Name Len: 6
+      'c',  'o',  'o',  'k',  'i', 'e',            // Name
+      0x08,                                        // Value Len: 7
+      'b',  'a',  'z',  '=',  'b', 'i', 'n', 'g',  // Value
+      0x00,                                        // Unindexed Entry
+      0x06,                                        // Name Len: 6
+      'c',                                         // Name (split)
+
+      0x00, 0x00, 0x12,             // Length: 18
+      0x09,                         //   Type: CONTINUATION
+      0x04,                         //  Flags: END_HEADERS
+      0x00, 0x00, 0x00, 0x01,       // Stream: 1
+      'o',  'o',  'k',  'i',  'e',  // Name (continued)
+      0x00,                         // Value Len: 0
+      0x00,                         // Unindexed Entry
+      0x04,                         // Name Len: 4
+      'n',  'a',  'm',  'e',        // Name
+      0x05,                         // Value Len: 5
+      'v',  'a',  'l',  'u',  'e',  // Value
+  };
+  // frame-format on
+
+  TestSpdyVisitor visitor(SpdyFramer::DISABLE_COMPRESSION);
+  visitor.SimulateInFramer(kInput, sizeof(kInput));
+
+  EXPECT_EQ(0, visitor.error_count_);
+  EXPECT_EQ(1u, visitor.last_push_promise_stream_);
+  EXPECT_EQ(42u, visitor.last_push_promise_promised_stream_);
+  EXPECT_EQ(2, visitor.continuation_count_);
+  EXPECT_EQ(0, visitor.zero_length_control_frame_header_data_count_);
+  EXPECT_EQ(0, visitor.end_of_stream_count_);
+
+  EXPECT_THAT(
+      visitor.headers_,
+      testing::ElementsAre(testing::Pair("cookie", "foo=bar; baz=bing; "),
+                           testing::Pair("name", "value")));
+}
+
+// Receiving an unknown frame when a continuation is expected should
+// result in a SPDY_UNEXPECTED_FRAME error
+TEST_P(SpdyFramerTest, ReceiveUnknownMidContinuation) {
+  const unsigned char kInput[] = {
+      0x00, 0x00, 0x10,        // Length: 16
+      0x01,                    //   Type: HEADERS
+      0x00,                    //  Flags: none
+      0x00, 0x00, 0x00, 0x01,  // Stream: 1
+      0x00, 0x06, 0x63, 0x6f,  // HPACK
+      0x6f, 0x6b, 0x69, 0x65,  //
+      0x07, 0x66, 0x6f, 0x6f,  //
+      0x3d, 0x62, 0x61, 0x72,  //
+
+      0x00, 0x00, 0x14,        // Length: 20
+      0xa9,                    //   Type: UnknownFrameType(169)
+      0x00,                    //  Flags: none
+      0x00, 0x00, 0x00, 0x01,  // Stream: 1
+      0x00, 0x06, 0x63, 0x6f,  // Payload
+      0x6f, 0x6b, 0x69, 0x65,  //
+      0x08, 0x62, 0x61, 0x7a,  //
+      0x3d, 0x62, 0x69, 0x6e,  //
+      0x67, 0x00, 0x06, 0x63,  //
+  };
+
+  TestSpdyVisitor visitor(SpdyFramer::DISABLE_COMPRESSION);
+  // Assume the unknown frame is allowed
+  visitor.on_unknown_frame_result_ = true;
+  deframer_.set_visitor(&visitor);
+  visitor.SimulateInFramer(kInput, sizeof(kInput));
+
+  EXPECT_EQ(1, visitor.error_count_);
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_UNEXPECTED_FRAME,
+            visitor.deframer_.spdy_framer_error())
+      << Http2DecoderAdapter::SpdyFramerErrorToString(
+             visitor.deframer_.spdy_framer_error());
+  EXPECT_EQ(1, visitor.headers_frame_count_);
+  EXPECT_EQ(0, visitor.continuation_count_);
+  EXPECT_EQ(0u, visitor.header_buffer_length_);
+}
+
+// Receiving an unknown frame when a continuation is expected should
+// result in a SPDY_UNEXPECTED_FRAME error
+TEST_P(SpdyFramerTest, ReceiveUnknownMidContinuationWithExtension) {
+  const unsigned char kInput[] = {
+      0x00, 0x00, 0x10,        // Length: 16
+      0x01,                    //   Type: HEADERS
+      0x00,                    //  Flags: none
+      0x00, 0x00, 0x00, 0x01,  // Stream: 1
+      0x00, 0x06, 0x63, 0x6f,  // HPACK
+      0x6f, 0x6b, 0x69, 0x65,  //
+      0x07, 0x66, 0x6f, 0x6f,  //
+      0x3d, 0x62, 0x61, 0x72,  //
+
+      0x00, 0x00, 0x14,        // Length: 20
+      0xa9,                    //   Type: UnknownFrameType(169)
+      0x00,                    //  Flags: none
+      0x00, 0x00, 0x00, 0x01,  // Stream: 1
+      0x00, 0x06, 0x63, 0x6f,  // Payload
+      0x6f, 0x6b, 0x69, 0x65,  //
+      0x08, 0x62, 0x61, 0x7a,  //
+      0x3d, 0x62, 0x69, 0x6e,  //
+      0x67, 0x00, 0x06, 0x63,  //
+  };
+
+  TestSpdyVisitor visitor(SpdyFramer::DISABLE_COMPRESSION);
+  TestExtension extension;
+  visitor.set_extension_visitor(&extension);
+  deframer_.set_visitor(&visitor);
+  visitor.SimulateInFramer(kInput, sizeof(kInput));
+
+  EXPECT_EQ(1, visitor.error_count_);
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_UNEXPECTED_FRAME,
+            visitor.deframer_.spdy_framer_error())
+      << Http2DecoderAdapter::SpdyFramerErrorToString(
+             visitor.deframer_.spdy_framer_error());
+  EXPECT_EQ(1, visitor.headers_frame_count_);
+  EXPECT_EQ(0, visitor.continuation_count_);
+  EXPECT_EQ(0u, visitor.header_buffer_length_);
+}
+
+TEST_P(SpdyFramerTest, ReceiveContinuationOnWrongStream) {
+  const unsigned char kInput[] = {
+      0x00, 0x00, 0x10,        // Length: 16
+      0x01,                    //   Type: HEADERS
+      0x00,                    //  Flags: none
+      0x00, 0x00, 0x00, 0x01,  // Stream: 1
+      0x00, 0x06, 0x63, 0x6f,  // HPACK
+      0x6f, 0x6b, 0x69, 0x65,  //
+      0x07, 0x66, 0x6f, 0x6f,  //
+      0x3d, 0x62, 0x61, 0x72,  //
+
+      0x00, 0x00, 0x14,        // Length: 20
+      0x09,                    //   Type: CONTINUATION
+      0x00,                    //  Flags: none
+      0x00, 0x00, 0x00, 0x02,  // Stream: 2
+      0x00, 0x06, 0x63, 0x6f,  // HPACK
+      0x6f, 0x6b, 0x69, 0x65,  //
+      0x08, 0x62, 0x61, 0x7a,  //
+      0x3d, 0x62, 0x69, 0x6e,  //
+      0x67, 0x00, 0x06, 0x63,  //
+  };
+
+  TestSpdyVisitor visitor(SpdyFramer::DISABLE_COMPRESSION);
+  deframer_.set_visitor(&visitor);
+  visitor.SimulateInFramer(kInput, sizeof(kInput));
+
+  EXPECT_EQ(1, visitor.error_count_);
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_UNEXPECTED_FRAME,
+            visitor.deframer_.spdy_framer_error())
+      << Http2DecoderAdapter::SpdyFramerErrorToString(
+             visitor.deframer_.spdy_framer_error());
+  EXPECT_EQ(1, visitor.headers_frame_count_);
+  EXPECT_EQ(0, visitor.continuation_count_);
+  EXPECT_EQ(0u, visitor.header_buffer_length_);
+}
+
+TEST_P(SpdyFramerTest, ReadContinuationOutOfOrder) {
+  const unsigned char kInput[] = {
+      0x00, 0x00, 0x18,        // Length: 24
+      0x09,                    //   Type: CONTINUATION
+      0x00,                    //  Flags: none
+      0x00, 0x00, 0x00, 0x01,  // Stream: 1
+      0x00, 0x06, 0x63, 0x6f,  // HPACK
+      0x6f, 0x6b, 0x69, 0x65,  //
+      0x07, 0x66, 0x6f, 0x6f,  //
+      0x3d, 0x62, 0x61, 0x72,  //
+  };
+
+  TestSpdyVisitor visitor(SpdyFramer::DISABLE_COMPRESSION);
+  deframer_.set_visitor(&visitor);
+  visitor.SimulateInFramer(kInput, sizeof(kInput));
+
+  EXPECT_EQ(1, visitor.error_count_);
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_UNEXPECTED_FRAME,
+            visitor.deframer_.spdy_framer_error())
+      << Http2DecoderAdapter::SpdyFramerErrorToString(
+             visitor.deframer_.spdy_framer_error());
+  EXPECT_EQ(0, visitor.continuation_count_);
+  EXPECT_EQ(0u, visitor.header_buffer_length_);
+}
+
+TEST_P(SpdyFramerTest, ExpectContinuationReceiveData) {
+  const unsigned char kInput[] = {
+      0x00, 0x00, 0x10,        // Length: 16
+      0x01,                    //   Type: HEADERS
+      0x00,                    //  Flags: none
+      0x00, 0x00, 0x00, 0x01,  // Stream: 1
+      0x00, 0x06, 0x63, 0x6f,  // HPACK
+      0x6f, 0x6b, 0x69, 0x65,  //
+      0x07, 0x66, 0x6f, 0x6f,  //
+      0x3d, 0x62, 0x61, 0x72,  //
+
+      0x00, 0x00, 0x00,        // Length: 0
+      0x00,                    //   Type: DATA
+      0x01,                    //  Flags: END_STREAM
+      0x00, 0x00, 0x00, 0x04,  // Stream: 4
+
+      0xde, 0xad, 0xbe, 0xef,  // Truncated Frame Header
+  };
+
+  TestSpdyVisitor visitor(SpdyFramer::DISABLE_COMPRESSION);
+  deframer_.set_visitor(&visitor);
+  visitor.SimulateInFramer(kInput, sizeof(kInput));
+
+  EXPECT_EQ(1, visitor.error_count_);
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_UNEXPECTED_FRAME,
+            visitor.deframer_.spdy_framer_error())
+      << Http2DecoderAdapter::SpdyFramerErrorToString(
+             visitor.deframer_.spdy_framer_error());
+  EXPECT_EQ(1, visitor.headers_frame_count_);
+  EXPECT_EQ(0, visitor.continuation_count_);
+  EXPECT_EQ(0u, visitor.header_buffer_length_);
+  EXPECT_EQ(0, visitor.data_frame_count_);
+}
+
+TEST_P(SpdyFramerTest, ExpectContinuationReceiveControlFrame) {
+  const unsigned char kInput[] = {
+      0x00, 0x00, 0x10,        // Length: 16
+      0x01,                    //   Type: HEADERS
+      0x00,                    //  Flags: none
+      0x00, 0x00, 0x00, 0x01,  // Stream: 1
+      0x00, 0x06, 0x63, 0x6f,  // HPACK
+      0x6f, 0x6b, 0x69, 0x65,  //
+      0x07, 0x66, 0x6f, 0x6f,  //
+      0x3d, 0x62, 0x61, 0x72,  //
+
+      0x00, 0x00, 0x10,        // Length: 16
+      0x01,                    //   Type: HEADERS
+      0x00,                    //  Flags: none
+      0x00, 0x00, 0x00, 0x01,  // Stream: 1
+      0x00, 0x06, 0x63, 0x6f,  // HPACK
+      0x6f, 0x6b, 0x69, 0x65,  //
+      0x07, 0x66, 0x6f, 0x6f,  //
+      0x3d, 0x62, 0x61, 0x72,  //
+  };
+
+  TestSpdyVisitor visitor(SpdyFramer::DISABLE_COMPRESSION);
+  deframer_.set_visitor(&visitor);
+  visitor.SimulateInFramer(kInput, sizeof(kInput));
+
+  EXPECT_EQ(1, visitor.error_count_);
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_UNEXPECTED_FRAME,
+            visitor.deframer_.spdy_framer_error())
+      << Http2DecoderAdapter::SpdyFramerErrorToString(
+             visitor.deframer_.spdy_framer_error());
+  EXPECT_EQ(1, visitor.headers_frame_count_);
+  EXPECT_EQ(0, visitor.continuation_count_);
+  EXPECT_EQ(0u, visitor.header_buffer_length_);
+  EXPECT_EQ(0, visitor.data_frame_count_);
+}
+
+TEST_P(SpdyFramerTest, ReadGarbage) {
+  unsigned char garbage_frame[256];
+  memset(garbage_frame, ~0, sizeof(garbage_frame));
+  TestSpdyVisitor visitor(SpdyFramer::DISABLE_COMPRESSION);
+  visitor.SimulateInFramer(garbage_frame, sizeof(garbage_frame));
+  EXPECT_EQ(1, visitor.error_count_);
+}
+
+TEST_P(SpdyFramerTest, ReadUnknownExtensionFrame) {
+  // The unrecognized frame type should still have a valid length.
+  const unsigned char unknown_frame[] = {
+      0x00, 0x00, 0x08,        // Length: 8
+      0xff,                    //   Type: UnknownFrameType(255)
+      0xff,                    //  Flags: 0xff
+      0xff, 0xff, 0xff, 0xff,  // Stream: 0x7fffffff (R-bit set)
+      0xff, 0xff, 0xff, 0xff,  // Payload
+      0xff, 0xff, 0xff, 0xff,  //
+  };
+  TestSpdyVisitor visitor(SpdyFramer::DISABLE_COMPRESSION);
+
+  // Simulate the case where the stream id validation checks out.
+  visitor.on_unknown_frame_result_ = true;
+  visitor.SimulateInFramer(unknown_frame, SPDY_ARRAYSIZE(unknown_frame));
+  EXPECT_EQ(0, visitor.error_count_);
+
+  // Follow it up with a valid control frame to make sure we handle
+  // subsequent frames correctly.
+  SpdySettingsIR settings_ir;
+  settings_ir.AddSetting(SETTINGS_HEADER_TABLE_SIZE, 10);
+  SpdySerializedFrame control_frame(framer_.SerializeSettings(settings_ir));
+  if (use_output_) {
+    ASSERT_TRUE(framer_.SerializeSettings(settings_ir, &output_));
+    control_frame = SpdySerializedFrame(output_.Begin(), output_.Size(), false);
+  }
+  visitor.SimulateInFramer(
+      reinterpret_cast<unsigned char*>(control_frame.data()),
+      control_frame.size());
+  EXPECT_EQ(0, visitor.error_count_);
+  EXPECT_EQ(1, visitor.setting_count_);
+  EXPECT_EQ(1, visitor.settings_ack_sent_);
+}
+
+TEST_P(SpdyFramerTest, ReadUnknownExtensionFrameWithExtension) {
+  // The unrecognized frame type should still have a valid length.
+  const unsigned char unknown_frame[] = {
+      0x00, 0x00, 0x14,        // Length: 20
+      0xff,                    //   Type: UnknownFrameType(255)
+      0xff,                    //  Flags: 0xff
+      0xff, 0xff, 0xff, 0xff,  // Stream: 0x7fffffff (R-bit set)
+      0xff, 0xff, 0xff, 0xff,  // Payload
+      0xff, 0xff, 0xff, 0xff,  //
+      0xff, 0xff, 0xff, 0xff,  //
+      0xff, 0xff, 0xff, 0xff,  //
+      0xff, 0xff, 0xff, 0xff,  //
+  };
+  TestSpdyVisitor visitor(SpdyFramer::DISABLE_COMPRESSION);
+  TestExtension extension;
+  visitor.set_extension_visitor(&extension);
+  visitor.SimulateInFramer(unknown_frame, SPDY_ARRAYSIZE(unknown_frame));
+  EXPECT_EQ(0, visitor.error_count_);
+  EXPECT_EQ(0x7fffffffu, extension.stream_id_);
+  EXPECT_EQ(20u, extension.length_);
+  EXPECT_EQ(255, extension.type_);
+  EXPECT_EQ(0xff, extension.flags_);
+  EXPECT_EQ(SpdyString(20, '\xff'), extension.payload_);
+
+  // Follow it up with a valid control frame to make sure we handle
+  // subsequent frames correctly.
+  SpdySettingsIR settings_ir;
+  settings_ir.AddSetting(SETTINGS_HEADER_TABLE_SIZE, 10);
+  SpdySerializedFrame control_frame(framer_.SerializeSettings(settings_ir));
+  visitor.SimulateInFramer(
+      reinterpret_cast<unsigned char*>(control_frame.data()),
+      control_frame.size());
+  EXPECT_EQ(0, visitor.error_count_);
+  EXPECT_EQ(1, visitor.setting_count_);
+  EXPECT_EQ(1, visitor.settings_ack_sent_);
+}
+
+TEST_P(SpdyFramerTest, ReadGarbageWithValidLength) {
+  const unsigned char kFrameData[] = {
+      0x00, 0x00, 0x08,        // Length: 8
+      0xff,                    //   Type: UnknownFrameType(255)
+      0xff,                    //  Flags: 0xff
+      0xff, 0xff, 0xff, 0xff,  // Stream: 0x7fffffff (R-bit set)
+      0xff, 0xff, 0xff, 0xff,  // Payload
+      0xff, 0xff, 0xff, 0xff,  //
+  };
+  TestSpdyVisitor visitor(SpdyFramer::DISABLE_COMPRESSION);
+  visitor.SimulateInFramer(kFrameData, SPDY_ARRAYSIZE(kFrameData));
+  EXPECT_EQ(1, visitor.error_count_);
+}
+
+TEST_P(SpdyFramerTest, ReadGarbageHPACKEncoding) {
+  const unsigned char kInput[] = {
+      0x00, 0x12, 0x01,        // Length: 4609
+      0x04,                    //   Type: SETTINGS
+      0x00,                    //  Flags: none
+      0x00, 0x00, 0x01, 0xef,  // Stream: 495
+      0xef, 0xff,              //  Param: 61439
+      0xff, 0xff, 0xff, 0xff,  //  Value: 4294967295
+      0xff, 0xff,              //  Param: 0xffff
+      0xff, 0xff, 0xff, 0xff,  //  Value: 4294967295
+      0xff, 0xff, 0xff, 0xff,  // Settings (Truncated)
+      0xff,                    //
+  };
+
+  TestSpdyVisitor visitor(SpdyFramer::DISABLE_COMPRESSION);
+  visitor.SimulateInFramer(kInput, SPDY_ARRAYSIZE(kInput));
+  EXPECT_EQ(1, visitor.error_count_);
+}
+
+TEST_P(SpdyFramerTest, SizesTest) {
+  EXPECT_EQ(9u, kFrameHeaderSize);
+  EXPECT_EQ(9u, kDataFrameMinimumSize);
+  EXPECT_EQ(9u, kHeadersFrameMinimumSize);
+  EXPECT_EQ(14u, kPriorityFrameSize);
+  EXPECT_EQ(13u, kRstStreamFrameSize);
+  EXPECT_EQ(9u, kSettingsFrameMinimumSize);
+  EXPECT_EQ(13u, kPushPromiseFrameMinimumSize);
+  EXPECT_EQ(17u, kPingFrameSize);
+  EXPECT_EQ(17u, kGoawayFrameMinimumSize);
+  EXPECT_EQ(13u, kWindowUpdateFrameSize);
+  EXPECT_EQ(9u, kContinuationFrameMinimumSize);
+  EXPECT_EQ(11u, kGetAltSvcFrameMinimumSize);
+  EXPECT_EQ(9u, kFrameMinimumSize);
+
+  EXPECT_EQ(16384u, kHttp2DefaultFramePayloadLimit);
+  EXPECT_EQ(16393u, kHttp2DefaultFrameSizeLimit);
+}
+
+TEST_P(SpdyFramerTest, StateToStringTest) {
+  EXPECT_STREQ("ERROR", Http2DecoderAdapter::StateToString(
+                            Http2DecoderAdapter::SPDY_ERROR));
+  EXPECT_STREQ("FRAME_COMPLETE", Http2DecoderAdapter::StateToString(
+                                     Http2DecoderAdapter::SPDY_FRAME_COMPLETE));
+  EXPECT_STREQ("READY_FOR_FRAME",
+               Http2DecoderAdapter::StateToString(
+                   Http2DecoderAdapter::SPDY_READY_FOR_FRAME));
+  EXPECT_STREQ("READING_COMMON_HEADER",
+               Http2DecoderAdapter::StateToString(
+                   Http2DecoderAdapter::SPDY_READING_COMMON_HEADER));
+  EXPECT_STREQ("CONTROL_FRAME_PAYLOAD",
+               Http2DecoderAdapter::StateToString(
+                   Http2DecoderAdapter::SPDY_CONTROL_FRAME_PAYLOAD));
+  EXPECT_STREQ("IGNORE_REMAINING_PAYLOAD",
+               Http2DecoderAdapter::StateToString(
+                   Http2DecoderAdapter::SPDY_IGNORE_REMAINING_PAYLOAD));
+  EXPECT_STREQ("FORWARD_STREAM_FRAME",
+               Http2DecoderAdapter::StateToString(
+                   Http2DecoderAdapter::SPDY_FORWARD_STREAM_FRAME));
+  EXPECT_STREQ(
+      "SPDY_CONTROL_FRAME_BEFORE_HEADER_BLOCK",
+      Http2DecoderAdapter::StateToString(
+          Http2DecoderAdapter::SPDY_CONTROL_FRAME_BEFORE_HEADER_BLOCK));
+  EXPECT_STREQ("SPDY_CONTROL_FRAME_HEADER_BLOCK",
+               Http2DecoderAdapter::StateToString(
+                   Http2DecoderAdapter::SPDY_CONTROL_FRAME_HEADER_BLOCK));
+  EXPECT_STREQ("SPDY_SETTINGS_FRAME_PAYLOAD",
+               Http2DecoderAdapter::StateToString(
+                   Http2DecoderAdapter::SPDY_SETTINGS_FRAME_PAYLOAD));
+  EXPECT_STREQ("SPDY_ALTSVC_FRAME_PAYLOAD",
+               Http2DecoderAdapter::StateToString(
+                   Http2DecoderAdapter::SPDY_ALTSVC_FRAME_PAYLOAD));
+  EXPECT_STREQ("UNKNOWN_STATE",
+               Http2DecoderAdapter::StateToString(
+                   Http2DecoderAdapter::SPDY_ALTSVC_FRAME_PAYLOAD + 1));
+}
+
+TEST_P(SpdyFramerTest, SpdyFramerErrorToStringTest) {
+  EXPECT_STREQ("NO_ERROR", Http2DecoderAdapter::SpdyFramerErrorToString(
+                               Http2DecoderAdapter::SPDY_NO_ERROR));
+  EXPECT_STREQ("INVALID_STREAM_ID",
+               Http2DecoderAdapter::SpdyFramerErrorToString(
+                   Http2DecoderAdapter::SPDY_INVALID_STREAM_ID));
+  EXPECT_STREQ("INVALID_CONTROL_FRAME",
+               Http2DecoderAdapter::SpdyFramerErrorToString(
+                   Http2DecoderAdapter::SPDY_INVALID_CONTROL_FRAME));
+  EXPECT_STREQ("CONTROL_PAYLOAD_TOO_LARGE",
+               Http2DecoderAdapter::SpdyFramerErrorToString(
+                   Http2DecoderAdapter::SPDY_CONTROL_PAYLOAD_TOO_LARGE));
+  EXPECT_STREQ("ZLIB_INIT_FAILURE",
+               Http2DecoderAdapter::SpdyFramerErrorToString(
+                   Http2DecoderAdapter::SPDY_ZLIB_INIT_FAILURE));
+  EXPECT_STREQ("UNSUPPORTED_VERSION",
+               Http2DecoderAdapter::SpdyFramerErrorToString(
+                   Http2DecoderAdapter::SPDY_UNSUPPORTED_VERSION));
+  EXPECT_STREQ("DECOMPRESS_FAILURE",
+               Http2DecoderAdapter::SpdyFramerErrorToString(
+                   Http2DecoderAdapter::SPDY_DECOMPRESS_FAILURE));
+  EXPECT_STREQ("COMPRESS_FAILURE",
+               Http2DecoderAdapter::SpdyFramerErrorToString(
+                   Http2DecoderAdapter::SPDY_COMPRESS_FAILURE));
+  EXPECT_STREQ("GOAWAY_FRAME_CORRUPT",
+               Http2DecoderAdapter::SpdyFramerErrorToString(
+                   Http2DecoderAdapter::SPDY_GOAWAY_FRAME_CORRUPT));
+  EXPECT_STREQ("RST_STREAM_FRAME_CORRUPT",
+               Http2DecoderAdapter::SpdyFramerErrorToString(
+                   Http2DecoderAdapter::SPDY_RST_STREAM_FRAME_CORRUPT));
+  EXPECT_STREQ("INVALID_PADDING",
+               Http2DecoderAdapter::SpdyFramerErrorToString(
+                   Http2DecoderAdapter::SPDY_INVALID_PADDING));
+  EXPECT_STREQ("INVALID_DATA_FRAME_FLAGS",
+               Http2DecoderAdapter::SpdyFramerErrorToString(
+                   Http2DecoderAdapter::SPDY_INVALID_DATA_FRAME_FLAGS));
+  EXPECT_STREQ("INVALID_CONTROL_FRAME_FLAGS",
+               Http2DecoderAdapter::SpdyFramerErrorToString(
+                   Http2DecoderAdapter::SPDY_INVALID_CONTROL_FRAME_FLAGS));
+  EXPECT_STREQ("UNEXPECTED_FRAME",
+               Http2DecoderAdapter::SpdyFramerErrorToString(
+                   Http2DecoderAdapter::SPDY_UNEXPECTED_FRAME));
+  EXPECT_STREQ("INTERNAL_FRAMER_ERROR",
+               Http2DecoderAdapter::SpdyFramerErrorToString(
+                   Http2DecoderAdapter::SPDY_INTERNAL_FRAMER_ERROR));
+  EXPECT_STREQ("INVALID_CONTROL_FRAME_SIZE",
+               Http2DecoderAdapter::SpdyFramerErrorToString(
+                   Http2DecoderAdapter::SPDY_INVALID_CONTROL_FRAME_SIZE));
+  EXPECT_STREQ("OVERSIZED_PAYLOAD",
+               Http2DecoderAdapter::SpdyFramerErrorToString(
+                   Http2DecoderAdapter::SPDY_OVERSIZED_PAYLOAD));
+  EXPECT_STREQ("UNKNOWN_ERROR", Http2DecoderAdapter::SpdyFramerErrorToString(
+                                    Http2DecoderAdapter::LAST_ERROR));
+  EXPECT_STREQ("UNKNOWN_ERROR",
+               Http2DecoderAdapter::SpdyFramerErrorToString(
+                   static_cast<Http2DecoderAdapter::SpdyFramerError>(
+                       Http2DecoderAdapter::LAST_ERROR + 1)));
+}
+
+TEST_P(SpdyFramerTest, DataFrameFlagsV4) {
+  uint8_t valid_data_flags = DATA_FLAG_FIN | DATA_FLAG_PADDED;
+
+  uint8_t flags = 0;
+  do {
+    SCOPED_TRACE(testing::Message()
+                 << "Flags " << std::hex << static_cast<int>(flags));
+
+    testing::StrictMock<test::MockSpdyFramerVisitor> visitor;
+
+    deframer_.set_visitor(&visitor);
+
+    SpdyDataIR data_ir(/* stream_id = */ 1, "hello");
+    SpdySerializedFrame frame(framer_.SerializeData(data_ir));
+    SetFrameFlags(&frame, flags);
+
+    if (flags & ~valid_data_flags) {
+      EXPECT_CALL(visitor, OnError(_));
+    } else {
+      EXPECT_CALL(visitor, OnDataFrameHeader(1, 5, flags & DATA_FLAG_FIN));
+      if (flags & DATA_FLAG_PADDED) {
+        // The first byte of payload is parsed as padding length, but 'h'
+        // (0x68) is too large a padding length for a 5 byte payload.
+        EXPECT_CALL(visitor, OnStreamPadding(_, 1));
+        // Expect Error since the frame ends prematurely.
+        EXPECT_CALL(visitor, OnError(_));
+      } else {
+        EXPECT_CALL(visitor, OnStreamFrameData(_, _, 5));
+        if (flags & DATA_FLAG_FIN) {
+          EXPECT_CALL(visitor, OnStreamEnd(_));
+        }
+      }
+    }
+
+    deframer_.ProcessInput(frame.data(), frame.size());
+    if (flags & ~valid_data_flags) {
+      EXPECT_EQ(Http2DecoderAdapter::SPDY_ERROR, deframer_.state());
+      EXPECT_EQ(Http2DecoderAdapter::SPDY_INVALID_DATA_FRAME_FLAGS,
+                deframer_.spdy_framer_error())
+          << Http2DecoderAdapter::SpdyFramerErrorToString(
+                 deframer_.spdy_framer_error());
+    } else if (flags & DATA_FLAG_PADDED) {
+      EXPECT_EQ(Http2DecoderAdapter::SPDY_ERROR, deframer_.state());
+      EXPECT_EQ(Http2DecoderAdapter::SPDY_INVALID_PADDING,
+                deframer_.spdy_framer_error())
+          << Http2DecoderAdapter::SpdyFramerErrorToString(
+                 deframer_.spdy_framer_error());
+    } else {
+      EXPECT_EQ(Http2DecoderAdapter::SPDY_READY_FOR_FRAME, deframer_.state());
+      EXPECT_EQ(Http2DecoderAdapter::SPDY_NO_ERROR,
+                deframer_.spdy_framer_error())
+          << Http2DecoderAdapter::SpdyFramerErrorToString(
+                 deframer_.spdy_framer_error());
+    }
+    deframer_.Reset();
+  } while (++flags != 0);
+}
+
+TEST_P(SpdyFramerTest, RstStreamFrameFlags) {
+  uint8_t flags = 0;
+  do {
+    SCOPED_TRACE(testing::Message()
+                 << "Flags " << std::hex << static_cast<int>(flags));
+
+    testing::StrictMock<test::MockSpdyFramerVisitor> visitor;
+    deframer_.set_visitor(&visitor);
+
+    SpdyRstStreamIR rst_stream(/* stream_id = */ 13, ERROR_CODE_CANCEL);
+    SpdySerializedFrame frame(framer_.SerializeRstStream(rst_stream));
+    if (use_output_) {
+      output_.Reset();
+      ASSERT_TRUE(framer_.SerializeRstStream(rst_stream, &output_));
+      frame = SpdySerializedFrame(output_.Begin(), output_.Size(), false);
+    }
+    SetFrameFlags(&frame, flags);
+
+    EXPECT_CALL(visitor, OnRstStream(13, ERROR_CODE_CANCEL));
+
+    deframer_.ProcessInput(frame.data(), frame.size());
+    EXPECT_EQ(Http2DecoderAdapter::SPDY_READY_FOR_FRAME, deframer_.state());
+    EXPECT_EQ(Http2DecoderAdapter::SPDY_NO_ERROR, deframer_.spdy_framer_error())
+        << Http2DecoderAdapter::SpdyFramerErrorToString(
+               deframer_.spdy_framer_error());
+    deframer_.Reset();
+  } while (++flags != 0);
+}
+
+TEST_P(SpdyFramerTest, SettingsFrameFlags) {
+  uint8_t flags = 0;
+  do {
+    SCOPED_TRACE(testing::Message()
+                 << "Flags " << std::hex << static_cast<int>(flags));
+
+    testing::StrictMock<test::MockSpdyFramerVisitor> visitor;
+    deframer_.set_visitor(&visitor);
+
+    SpdySettingsIR settings_ir;
+    settings_ir.AddSetting(SETTINGS_INITIAL_WINDOW_SIZE, 16);
+    SpdySerializedFrame frame(framer_.SerializeSettings(settings_ir));
+    if (use_output_) {
+      output_.Reset();
+      ASSERT_TRUE(framer_.SerializeSettings(settings_ir, &output_));
+      frame = SpdySerializedFrame(output_.Begin(), output_.Size(), false);
+    }
+    SetFrameFlags(&frame, flags);
+
+    if (flags & SETTINGS_FLAG_ACK) {
+      EXPECT_CALL(visitor, OnError(_));
+    } else {
+      EXPECT_CALL(visitor, OnSettings());
+      EXPECT_CALL(visitor, OnSetting(SETTINGS_INITIAL_WINDOW_SIZE, 16));
+      EXPECT_CALL(visitor, OnSettingsEnd());
+    }
+
+    deframer_.ProcessInput(frame.data(), frame.size());
+    if (flags & SETTINGS_FLAG_ACK) {
+      // The frame is invalid because ACK frames should have no payload.
+      EXPECT_EQ(Http2DecoderAdapter::SPDY_ERROR, deframer_.state());
+      EXPECT_EQ(Http2DecoderAdapter::SPDY_INVALID_CONTROL_FRAME_SIZE,
+                deframer_.spdy_framer_error())
+          << Http2DecoderAdapter::SpdyFramerErrorToString(
+                 deframer_.spdy_framer_error());
+    } else {
+      EXPECT_EQ(Http2DecoderAdapter::SPDY_READY_FOR_FRAME, deframer_.state());
+      EXPECT_EQ(Http2DecoderAdapter::SPDY_NO_ERROR,
+                deframer_.spdy_framer_error())
+          << Http2DecoderAdapter::SpdyFramerErrorToString(
+                 deframer_.spdy_framer_error());
+    }
+    deframer_.Reset();
+  } while (++flags != 0);
+}
+
+TEST_P(SpdyFramerTest, GoawayFrameFlags) {
+  uint8_t flags = 0;
+  do {
+    SCOPED_TRACE(testing::Message()
+                 << "Flags " << std::hex << static_cast<int>(flags));
+
+    testing::StrictMock<test::MockSpdyFramerVisitor> visitor;
+
+    deframer_.set_visitor(&visitor);
+
+    SpdyGoAwayIR goaway_ir(/* last_good_stream_id = */ 97, ERROR_CODE_NO_ERROR,
+                           "test");
+    SpdySerializedFrame frame(framer_.SerializeGoAway(goaway_ir));
+    if (use_output_) {
+      output_.Reset();
+      ASSERT_TRUE(framer_.SerializeGoAway(goaway_ir, &output_));
+      frame = SpdySerializedFrame(output_.Begin(), output_.Size(), false);
+    }
+    SetFrameFlags(&frame, flags);
+
+    EXPECT_CALL(visitor, OnGoAway(97, ERROR_CODE_NO_ERROR));
+
+    deframer_.ProcessInput(frame.data(), frame.size());
+    EXPECT_EQ(Http2DecoderAdapter::SPDY_READY_FOR_FRAME, deframer_.state());
+    EXPECT_EQ(Http2DecoderAdapter::SPDY_NO_ERROR, deframer_.spdy_framer_error())
+        << Http2DecoderAdapter::SpdyFramerErrorToString(
+               deframer_.spdy_framer_error());
+    deframer_.Reset();
+  } while (++flags != 0);
+}
+
+TEST_P(SpdyFramerTest, HeadersFrameFlags) {
+  uint8_t flags = 0;
+  do {
+    SCOPED_TRACE(testing::Message()
+                 << "Flags " << std::hex << static_cast<int>(flags));
+
+    testing::StrictMock<test::MockSpdyFramerVisitor> visitor;
+    SpdyFramer framer(SpdyFramer::ENABLE_COMPRESSION);
+    Http2DecoderAdapter deframer;
+    deframer.set_visitor(&visitor);
+
+    SpdyHeadersIR headers_ir(/* stream_id = */ 57);
+    if (flags & HEADERS_FLAG_PRIORITY) {
+      headers_ir.set_weight(3);
+      headers_ir.set_has_priority(true);
+      headers_ir.set_parent_stream_id(5);
+      headers_ir.set_exclusive(true);
+    }
+    headers_ir.SetHeader("foo", "bar");
+    SpdySerializedFrame frame(SpdyFramerPeer::SerializeHeaders(
+        &framer, headers_ir, use_output_ ? &output_ : nullptr));
+    uint8_t set_flags = flags & ~HEADERS_FLAG_PADDED;
+    SetFrameFlags(&frame, set_flags);
+
+    // Expected callback values
+    SpdyStreamId stream_id = 57;
+    bool has_priority = false;
+    int weight = 0;
+    SpdyStreamId parent_stream_id = 0;
+    bool exclusive = false;
+    bool fin = flags & CONTROL_FLAG_FIN;
+    bool end = flags & HEADERS_FLAG_END_HEADERS;
+    if (flags & HEADERS_FLAG_PRIORITY) {
+      has_priority = true;
+      weight = 3;
+      parent_stream_id = 5;
+      exclusive = true;
+    }
+    EXPECT_CALL(visitor, OnHeaders(stream_id, has_priority, weight,
+                                   parent_stream_id, exclusive, fin, end));
+    EXPECT_CALL(visitor, OnHeaderFrameStart(57)).Times(1);
+    if (end) {
+      EXPECT_CALL(visitor, OnHeaderFrameEnd(57)).Times(1);
+    }
+    if (flags & DATA_FLAG_FIN && end) {
+      EXPECT_CALL(visitor, OnStreamEnd(_));
+    } else {
+      // Do not close the stream if we are expecting a CONTINUATION frame.
+      EXPECT_CALL(visitor, OnStreamEnd(_)).Times(0);
+    }
+
+    deframer.ProcessInput(frame.data(), frame.size());
+    EXPECT_EQ(Http2DecoderAdapter::SPDY_READY_FOR_FRAME, deframer.state());
+    EXPECT_EQ(Http2DecoderAdapter::SPDY_NO_ERROR, deframer.spdy_framer_error())
+        << Http2DecoderAdapter::SpdyFramerErrorToString(
+               deframer.spdy_framer_error());
+    deframer.Reset();
+  } while (++flags != 0);
+}
+
+TEST_P(SpdyFramerTest, PingFrameFlags) {
+  uint8_t flags = 0;
+  do {
+    SCOPED_TRACE(testing::Message()
+                 << "Flags " << std::hex << static_cast<int>(flags));
+
+    testing::StrictMock<test::MockSpdyFramerVisitor> visitor;
+    deframer_.set_visitor(&visitor);
+
+    SpdySerializedFrame frame(framer_.SerializePing(SpdyPingIR(42)));
+    SetFrameFlags(&frame, flags);
+
+    EXPECT_CALL(visitor, OnPing(42, flags & PING_FLAG_ACK));
+
+    deframer_.ProcessInput(frame.data(), frame.size());
+    EXPECT_EQ(Http2DecoderAdapter::SPDY_READY_FOR_FRAME, deframer_.state());
+    EXPECT_EQ(Http2DecoderAdapter::SPDY_NO_ERROR, deframer_.spdy_framer_error())
+        << Http2DecoderAdapter::SpdyFramerErrorToString(
+               deframer_.spdy_framer_error());
+    deframer_.Reset();
+  } while (++flags != 0);
+}
+
+TEST_P(SpdyFramerTest, WindowUpdateFrameFlags) {
+  uint8_t flags = 0;
+  do {
+    SCOPED_TRACE(testing::Message()
+                 << "Flags " << std::hex << static_cast<int>(flags));
+
+    testing::StrictMock<test::MockSpdyFramerVisitor> visitor;
+
+    deframer_.set_visitor(&visitor);
+
+    SpdySerializedFrame frame(framer_.SerializeWindowUpdate(
+        SpdyWindowUpdateIR(/* stream_id = */ 4, /* delta = */ 1024)));
+    SetFrameFlags(&frame, flags);
+
+    EXPECT_CALL(visitor, OnWindowUpdate(4, 1024));
+
+    deframer_.ProcessInput(frame.data(), frame.size());
+    EXPECT_EQ(Http2DecoderAdapter::SPDY_READY_FOR_FRAME, deframer_.state());
+    EXPECT_EQ(Http2DecoderAdapter::SPDY_NO_ERROR, deframer_.spdy_framer_error())
+        << Http2DecoderAdapter::SpdyFramerErrorToString(
+               deframer_.spdy_framer_error());
+    deframer_.Reset();
+  } while (++flags != 0);
+}
+
+TEST_P(SpdyFramerTest, PushPromiseFrameFlags) {
+  const SpdyStreamId client_id = 123;   // Must be odd.
+  const SpdyStreamId promised_id = 22;  // Must be even.
+  uint8_t flags = 0;
+  do {
+    SCOPED_TRACE(testing::Message()
+                 << "Flags " << std::hex << static_cast<int>(flags));
+
+    testing::StrictMock<test::MockSpdyFramerVisitor> visitor;
+    testing::StrictMock<test::MockDebugVisitor> debug_visitor;
+    SpdyFramer framer(SpdyFramer::ENABLE_COMPRESSION);
+    Http2DecoderAdapter deframer;
+    deframer.set_visitor(&visitor);
+    deframer.set_debug_visitor(&debug_visitor);
+    framer.set_debug_visitor(&debug_visitor);
+
+    EXPECT_CALL(
+        debug_visitor,
+        OnSendCompressedFrame(client_id, SpdyFrameType::PUSH_PROMISE, _, _));
+
+    SpdyPushPromiseIR push_promise(client_id, promised_id);
+    push_promise.SetHeader("foo", "bar");
+    SpdySerializedFrame frame(SpdyFramerPeer::SerializePushPromise(
+        &framer, push_promise, use_output_ ? &output_ : nullptr));
+    // TODO(jgraettinger): Add padding to SpdyPushPromiseIR,
+    // and implement framing.
+    SetFrameFlags(&frame, flags & ~HEADERS_FLAG_PADDED);
+
+    bool end = flags & PUSH_PROMISE_FLAG_END_PUSH_PROMISE;
+    EXPECT_CALL(debug_visitor, OnReceiveCompressedFrame(
+                                   client_id, SpdyFrameType::PUSH_PROMISE, _));
+    EXPECT_CALL(visitor, OnPushPromise(client_id, promised_id, end));
+    EXPECT_CALL(visitor, OnHeaderFrameStart(client_id)).Times(1);
+    if (end) {
+      EXPECT_CALL(visitor, OnHeaderFrameEnd(client_id)).Times(1);
+    }
+
+    deframer.ProcessInput(frame.data(), frame.size());
+    EXPECT_EQ(Http2DecoderAdapter::SPDY_READY_FOR_FRAME, deframer.state());
+    EXPECT_EQ(Http2DecoderAdapter::SPDY_NO_ERROR, deframer.spdy_framer_error())
+        << Http2DecoderAdapter::SpdyFramerErrorToString(
+               deframer.spdy_framer_error());
+  } while (++flags != 0);
+}
+
+TEST_P(SpdyFramerTest, ContinuationFrameFlags) {
+  uint8_t flags = 0;
+  do {
+    if (use_output_) {
+      output_.Reset();
+    }
+    SCOPED_TRACE(testing::Message()
+                 << "Flags " << std::hex << static_cast<int>(flags));
+
+    testing::StrictMock<test::MockSpdyFramerVisitor> visitor;
+    testing::StrictMock<test::MockDebugVisitor> debug_visitor;
+    SpdyFramer framer(SpdyFramer::ENABLE_COMPRESSION);
+    Http2DecoderAdapter deframer;
+    deframer.set_visitor(&visitor);
+    deframer.set_debug_visitor(&debug_visitor);
+    framer.set_debug_visitor(&debug_visitor);
+
+    EXPECT_CALL(debug_visitor,
+                OnSendCompressedFrame(42, SpdyFrameType::HEADERS, _, _));
+    EXPECT_CALL(debug_visitor,
+                OnReceiveCompressedFrame(42, SpdyFrameType::HEADERS, _));
+    EXPECT_CALL(visitor, OnHeaders(42, false, 0, 0, false, false, false));
+    EXPECT_CALL(visitor, OnHeaderFrameStart(42)).Times(1);
+
+    SpdyHeadersIR headers_ir(/* stream_id = */ 42);
+    headers_ir.SetHeader("foo", "bar");
+    SpdySerializedFrame frame0;
+    if (use_output_) {
+      EXPECT_TRUE(framer.SerializeHeaders(headers_ir, &output_));
+      frame0 = SpdySerializedFrame(output_.Begin(), output_.Size(), false);
+    } else {
+      frame0 = framer.SerializeHeaders(headers_ir);
+    }
+    SetFrameFlags(&frame0, 0);
+
+    SpdyContinuationIR continuation(/* stream_id = */ 42);
+    SpdySerializedFrame frame1;
+    if (use_output_) {
+      char* begin = output_.Begin() + output_.Size();
+      ASSERT_TRUE(framer.SerializeContinuation(continuation, &output_));
+      frame1 =
+          SpdySerializedFrame(begin, output_.Size() - frame0.size(), false);
+    } else {
+      frame1 = framer.SerializeContinuation(continuation);
+    }
+    SetFrameFlags(&frame1, flags);
+
+    EXPECT_CALL(debug_visitor,
+                OnReceiveCompressedFrame(42, SpdyFrameType::CONTINUATION, _));
+    EXPECT_CALL(visitor, OnContinuation(42, flags & HEADERS_FLAG_END_HEADERS));
+    bool end = flags & HEADERS_FLAG_END_HEADERS;
+    if (end) {
+      EXPECT_CALL(visitor, OnHeaderFrameEnd(42)).Times(1);
+    }
+
+    deframer.ProcessInput(frame0.data(), frame0.size());
+    deframer.ProcessInput(frame1.data(), frame1.size());
+    EXPECT_EQ(Http2DecoderAdapter::SPDY_READY_FOR_FRAME, deframer.state());
+    EXPECT_EQ(Http2DecoderAdapter::SPDY_NO_ERROR, deframer.spdy_framer_error())
+        << Http2DecoderAdapter::SpdyFramerErrorToString(
+               deframer.spdy_framer_error());
+  } while (++flags != 0);
+}
+
+// TODO(mlavan): Add TEST_P(SpdyFramerTest, AltSvcFrameFlags)
+
+// Test handling of a RST_STREAM with out-of-bounds status codes.
+TEST_P(SpdyFramerTest, RstStreamStatusBounds) {
+  const unsigned char kH2RstStreamInvalid[] = {
+      0x00, 0x00, 0x04,        // Length: 4
+      0x03,                    //   Type: RST_STREAM
+      0x00,                    //  Flags: none
+      0x00, 0x00, 0x00, 0x01,  // Stream: 1
+      0x00, 0x00, 0x00, 0x00,  //  Error: NO_ERROR
+  };
+  const unsigned char kH2RstStreamNumStatusCodes[] = {
+      0x00, 0x00, 0x04,        // Length: 4
+      0x03,                    //   Type: RST_STREAM
+      0x00,                    //  Flags: none
+      0x00, 0x00, 0x00, 0x01,  // Stream: 1
+      0x00, 0x00, 0x00, 0xff,  //  Error: 255
+  };
+
+  testing::StrictMock<test::MockSpdyFramerVisitor> visitor;
+  deframer_.set_visitor(&visitor);
+
+  EXPECT_CALL(visitor, OnRstStream(1, ERROR_CODE_NO_ERROR));
+  deframer_.ProcessInput(reinterpret_cast<const char*>(kH2RstStreamInvalid),
+                         SPDY_ARRAYSIZE(kH2RstStreamInvalid));
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_READY_FOR_FRAME, deframer_.state());
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_NO_ERROR, deframer_.spdy_framer_error())
+      << Http2DecoderAdapter::SpdyFramerErrorToString(
+             deframer_.spdy_framer_error());
+  deframer_.Reset();
+
+  EXPECT_CALL(visitor, OnRstStream(1, ERROR_CODE_INTERNAL_ERROR));
+  deframer_.ProcessInput(
+      reinterpret_cast<const char*>(kH2RstStreamNumStatusCodes),
+      SPDY_ARRAYSIZE(kH2RstStreamNumStatusCodes));
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_READY_FOR_FRAME, deframer_.state());
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_NO_ERROR, deframer_.spdy_framer_error())
+      << Http2DecoderAdapter::SpdyFramerErrorToString(
+             deframer_.spdy_framer_error());
+}
+
+// Test handling of GOAWAY frames with out-of-bounds status code.
+TEST_P(SpdyFramerTest, GoAwayStatusBounds) {
+  const unsigned char kH2FrameData[] = {
+      0x00, 0x00, 0x0a,        // Length: 10
+      0x07,                    //   Type: GOAWAY
+      0x00,                    //  Flags: none
+      0x00, 0x00, 0x00, 0x00,  // Stream: 0
+      0x00, 0x00, 0x00, 0x01,  //   Last: 1
+      0xff, 0xff, 0xff, 0xff,  //  Error: 0xffffffff
+      0x47, 0x41,              // Description
+  };
+  testing::StrictMock<test::MockSpdyFramerVisitor> visitor;
+  deframer_.set_visitor(&visitor);
+
+  EXPECT_CALL(visitor, OnGoAway(1, ERROR_CODE_INTERNAL_ERROR));
+  deframer_.ProcessInput(reinterpret_cast<const char*>(kH2FrameData),
+                         SPDY_ARRAYSIZE(kH2FrameData));
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_READY_FOR_FRAME, deframer_.state());
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_NO_ERROR, deframer_.spdy_framer_error())
+      << Http2DecoderAdapter::SpdyFramerErrorToString(
+             deframer_.spdy_framer_error());
+}
+
+// Tests handling of a GOAWAY frame with out-of-bounds stream ID.
+TEST_P(SpdyFramerTest, GoAwayStreamIdBounds) {
+  const unsigned char kH2FrameData[] = {
+      0x00, 0x00, 0x08,        // Length: 8
+      0x07,                    //   Type: GOAWAY
+      0x00,                    //  Flags: none
+      0x00, 0x00, 0x00, 0x00,  // Stream: 0
+      0xff, 0xff, 0xff, 0xff,  //   Last: 0x7fffffff (R-bit set)
+      0x00, 0x00, 0x00, 0x00,  //  Error: NO_ERROR
+  };
+
+  testing::StrictMock<test::MockSpdyFramerVisitor> visitor;
+
+  deframer_.set_visitor(&visitor);
+
+  EXPECT_CALL(visitor, OnGoAway(0x7fffffff, ERROR_CODE_NO_ERROR));
+  deframer_.ProcessInput(reinterpret_cast<const char*>(kH2FrameData),
+                         SPDY_ARRAYSIZE(kH2FrameData));
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_READY_FOR_FRAME, deframer_.state());
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_NO_ERROR, deframer_.spdy_framer_error())
+      << Http2DecoderAdapter::SpdyFramerErrorToString(
+             deframer_.spdy_framer_error());
+}
+
+TEST_P(SpdyFramerTest, OnAltSvcWithOrigin) {
+  const SpdyStreamId kStreamId = 0;  // Stream id must be zero if origin given.
+
+  testing::StrictMock<test::MockSpdyFramerVisitor> visitor;
+
+  deframer_.set_visitor(&visitor);
+
+  SpdyAltSvcWireFormat::AlternativeService altsvc1(
+      "pid1", "host", 443, 5, SpdyAltSvcWireFormat::VersionVector());
+  SpdyAltSvcWireFormat::AlternativeService altsvc2(
+      "p\"=i:d", "h_\\o\"st", 123, 42, SpdyAltSvcWireFormat::VersionVector{24});
+  SpdyAltSvcWireFormat::AlternativeServiceVector altsvc_vector;
+  altsvc_vector.push_back(altsvc1);
+  altsvc_vector.push_back(altsvc2);
+  EXPECT_CALL(visitor,
+              OnAltSvc(kStreamId, SpdyStringPiece("o_r|g!n"), altsvc_vector));
+
+  SpdyAltSvcIR altsvc_ir(kStreamId);
+  altsvc_ir.set_origin("o_r|g!n");
+  altsvc_ir.add_altsvc(altsvc1);
+  altsvc_ir.add_altsvc(altsvc2);
+  SpdySerializedFrame frame(framer_.SerializeFrame(altsvc_ir));
+  if (use_output_) {
+    output_.Reset();
+    EXPECT_EQ(framer_.SerializeFrame(altsvc_ir, &output_), frame.size());
+    frame = SpdySerializedFrame(output_.Begin(), output_.Size(), false);
+  }
+  deframer_.ProcessInput(frame.data(), frame.size());
+
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_READY_FOR_FRAME, deframer_.state());
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_NO_ERROR, deframer_.spdy_framer_error())
+      << Http2DecoderAdapter::SpdyFramerErrorToString(
+             deframer_.spdy_framer_error());
+}
+
+TEST_P(SpdyFramerTest, OnAltSvcNoOrigin) {
+  const SpdyStreamId kStreamId = 1;
+
+  testing::StrictMock<test::MockSpdyFramerVisitor> visitor;
+
+  deframer_.set_visitor(&visitor);
+
+  SpdyAltSvcWireFormat::AlternativeService altsvc1(
+      "pid1", "host", 443, 5, SpdyAltSvcWireFormat::VersionVector());
+  SpdyAltSvcWireFormat::AlternativeService altsvc2(
+      "p\"=i:d", "h_\\o\"st", 123, 42, SpdyAltSvcWireFormat::VersionVector{24});
+  SpdyAltSvcWireFormat::AlternativeServiceVector altsvc_vector;
+  altsvc_vector.push_back(altsvc1);
+  altsvc_vector.push_back(altsvc2);
+  EXPECT_CALL(visitor, OnAltSvc(kStreamId, SpdyStringPiece(""), altsvc_vector));
+
+  SpdyAltSvcIR altsvc_ir(kStreamId);
+  altsvc_ir.add_altsvc(altsvc1);
+  altsvc_ir.add_altsvc(altsvc2);
+  SpdySerializedFrame frame(framer_.SerializeFrame(altsvc_ir));
+  deframer_.ProcessInput(frame.data(), frame.size());
+
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_READY_FOR_FRAME, deframer_.state());
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_NO_ERROR, deframer_.spdy_framer_error())
+      << Http2DecoderAdapter::SpdyFramerErrorToString(
+             deframer_.spdy_framer_error());
+}
+
+TEST_P(SpdyFramerTest, OnAltSvcEmptyProtocolId) {
+  const SpdyStreamId kStreamId = 0;  // Stream id must be zero if origin given.
+
+  testing::StrictMock<test::MockSpdyFramerVisitor> visitor;
+
+  deframer_.set_visitor(&visitor);
+
+  EXPECT_CALL(visitor,
+              OnError(Http2DecoderAdapter::SPDY_INVALID_CONTROL_FRAME));
+
+  SpdyAltSvcIR altsvc_ir(kStreamId);
+  altsvc_ir.set_origin("o1");
+  altsvc_ir.add_altsvc(SpdyAltSvcWireFormat::AlternativeService(
+      "pid1", "host", 443, 5, SpdyAltSvcWireFormat::VersionVector()));
+  altsvc_ir.add_altsvc(SpdyAltSvcWireFormat::AlternativeService(
+      "", "h1", 443, 10, SpdyAltSvcWireFormat::VersionVector()));
+  SpdySerializedFrame frame(framer_.SerializeFrame(altsvc_ir));
+  if (use_output_) {
+    output_.Reset();
+    EXPECT_EQ(framer_.SerializeFrame(altsvc_ir, &output_), frame.size());
+    frame = SpdySerializedFrame(output_.Begin(), output_.Size(), false);
+  }
+  deframer_.ProcessInput(frame.data(), frame.size());
+
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_ERROR, deframer_.state());
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_INVALID_CONTROL_FRAME,
+            deframer_.spdy_framer_error())
+      << Http2DecoderAdapter::SpdyFramerErrorToString(
+             deframer_.spdy_framer_error());
+}
+
+TEST_P(SpdyFramerTest, OnAltSvcBadLengths) {
+  const unsigned char kType = SerializeFrameType(SpdyFrameType::ALTSVC);
+  const unsigned char kFrameDataOriginLenLargerThanFrame[] = {
+      0x00, 0x00, 0x05, kType, 0x00, 0x00, 0x00,
+      0x00, 0x03, 0x42, 0x42,  'f',  'o',  'o',
+  };
+
+  TestSpdyVisitor visitor(SpdyFramer::DISABLE_COMPRESSION);
+
+  deframer_.set_visitor(&visitor);
+  visitor.SimulateInFramer(kFrameDataOriginLenLargerThanFrame,
+                           sizeof(kFrameDataOriginLenLargerThanFrame));
+
+  EXPECT_EQ(1, visitor.error_count_);
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_INVALID_CONTROL_FRAME,
+            visitor.deframer_.spdy_framer_error());
+}
+
+// Tests handling of ALTSVC frames delivered in small chunks.
+TEST_P(SpdyFramerTest, ReadChunkedAltSvcFrame) {
+  SpdyAltSvcIR altsvc_ir(/* stream_id = */ 1);
+  SpdyAltSvcWireFormat::AlternativeService altsvc1(
+      "pid1", "host", 443, 5, SpdyAltSvcWireFormat::VersionVector());
+  SpdyAltSvcWireFormat::AlternativeService altsvc2(
+      "p\"=i:d", "h_\\o\"st", 123, 42, SpdyAltSvcWireFormat::VersionVector{24});
+  altsvc_ir.add_altsvc(altsvc1);
+  altsvc_ir.add_altsvc(altsvc2);
+
+  SpdySerializedFrame control_frame(framer_.SerializeAltSvc(altsvc_ir));
+  TestSpdyVisitor visitor(SpdyFramer::DISABLE_COMPRESSION);
+
+  // Read data in small chunks.
+  size_t framed_data = 0;
+  size_t unframed_data = control_frame.size();
+  size_t kReadChunkSize = 5;  // Read five bytes at a time.
+  while (unframed_data > 0) {
+    size_t to_read = std::min(kReadChunkSize, unframed_data);
+    visitor.SimulateInFramer(
+        reinterpret_cast<unsigned char*>(control_frame.data() + framed_data),
+        to_read);
+    unframed_data -= to_read;
+    framed_data += to_read;
+  }
+  EXPECT_EQ(0, visitor.error_count_);
+  EXPECT_EQ(1, visitor.altsvc_count_);
+  ASSERT_NE(nullptr, visitor.test_altsvc_ir_);
+  ASSERT_EQ(2u, visitor.test_altsvc_ir_->altsvc_vector().size());
+  EXPECT_TRUE(visitor.test_altsvc_ir_->altsvc_vector()[0] == altsvc1);
+  EXPECT_TRUE(visitor.test_altsvc_ir_->altsvc_vector()[1] == altsvc2);
+}
+
+// While RFC7838 Section 4 says that an ALTSVC frame on stream 0 with empty
+// origin MUST be ignored, it is not implemented at the framer level: instead,
+// such frames are passed on to the consumer.
+TEST_P(SpdyFramerTest, ReadAltSvcFrame) {
+  constexpr struct {
+    uint32_t stream_id;
+    const char* origin;
+  } test_cases[] = {{0, ""},
+                    {1, ""},
+                    {0, "https://www.example.com"},
+                    {1, "https://www.example.com"}};
+  for (const auto& test_case : test_cases) {
+    SpdyAltSvcIR altsvc_ir(test_case.stream_id);
+    SpdyAltSvcWireFormat::AlternativeService altsvc(
+        "pid1", "host", 443, 5, SpdyAltSvcWireFormat::VersionVector());
+    altsvc_ir.add_altsvc(altsvc);
+    altsvc_ir.set_origin(test_case.origin);
+    SpdySerializedFrame frame(framer_.SerializeAltSvc(altsvc_ir));
+
+    TestSpdyVisitor visitor(SpdyFramer::ENABLE_COMPRESSION);
+    deframer_.set_visitor(&visitor);
+    deframer_.ProcessInput(frame.data(), frame.size());
+
+    EXPECT_EQ(0, visitor.error_count_);
+    EXPECT_EQ(1, visitor.altsvc_count_);
+    EXPECT_EQ(Http2DecoderAdapter::SPDY_READY_FOR_FRAME, deframer_.state());
+    EXPECT_EQ(Http2DecoderAdapter::SPDY_NO_ERROR, deframer_.spdy_framer_error())
+        << Http2DecoderAdapter::SpdyFramerErrorToString(
+               deframer_.spdy_framer_error());
+  }
+}
+
+// An ALTSVC frame with invalid Alt-Svc-Field-Value results in an error.
+TEST_P(SpdyFramerTest, ErrorOnAltSvcFrameWithInvalidValue) {
+  // Alt-Svc-Field-Value must be "clear" or must contain an "=" character
+  // per RFC7838 Section 3.
+  const char kFrameData[] = {
+      0x00, 0x00, 0x16,        //     Length: 22
+      0x0a,                    //       Type: ALTSVC
+      0x00,                    //      Flags: none
+      0x00, 0x00, 0x00, 0x01,  //     Stream: 1
+      0x00, 0x00,              // Origin-Len: 0
+      0x74, 0x68, 0x69, 0x73,  // thisisnotavalidvalue
+      0x69, 0x73, 0x6e, 0x6f, 0x74, 0x61, 0x76, 0x61,
+      0x6c, 0x69, 0x64, 0x76, 0x61, 0x6c, 0x75, 0x65,
+  };
+
+  TestSpdyVisitor visitor(SpdyFramer::ENABLE_COMPRESSION);
+  deframer_.set_visitor(&visitor);
+  deframer_.ProcessInput(kFrameData, sizeof(kFrameData));
+
+  EXPECT_EQ(1, visitor.error_count_);
+  EXPECT_EQ(0, visitor.altsvc_count_);
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_ERROR, deframer_.state());
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_INVALID_CONTROL_FRAME,
+            deframer_.spdy_framer_error())
+      << Http2DecoderAdapter::SpdyFramerErrorToString(
+             deframer_.spdy_framer_error());
+}
+
+// Tests handling of PRIORITY frames.
+TEST_P(SpdyFramerTest, ReadPriority) {
+  SpdyPriorityIR priority(/* stream_id = */ 3,
+                          /* parent_stream_id = */ 1,
+                          /* weight = */ 256,
+                          /* exclusive = */ false);
+  SpdySerializedFrame frame(framer_.SerializePriority(priority));
+  if (use_output_) {
+    output_.Reset();
+    ASSERT_TRUE(framer_.SerializePriority(priority, &output_));
+    frame = SpdySerializedFrame(output_.Begin(), output_.Size(), false);
+  }
+  testing::StrictMock<test::MockSpdyFramerVisitor> visitor;
+  deframer_.set_visitor(&visitor);
+  EXPECT_CALL(visitor, OnPriority(3, 1, 256, false));
+  deframer_.ProcessInput(frame.data(), frame.size());
+
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_READY_FOR_FRAME, deframer_.state());
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_NO_ERROR, deframer_.spdy_framer_error())
+      << Http2DecoderAdapter::SpdyFramerErrorToString(
+             deframer_.spdy_framer_error());
+}
+
+// Tests handling of PRIORITY frame with incorrect size.
+TEST_P(SpdyFramerTest, ReadIncorrectlySizedPriority) {
+  // PRIORITY frame of size 4, which isn't correct.
+  const unsigned char kFrameData[] = {
+      0x00, 0x00, 0x04,        // Length: 4
+      0x02,                    //   Type: PRIORITY
+      0x00,                    //  Flags: none
+      0x00, 0x00, 0x00, 0x03,  // Stream: 3
+      0x00, 0x00, 0x00, 0x01,  // Priority (Truncated)
+  };
+
+  TestSpdyVisitor visitor(SpdyFramer::DISABLE_COMPRESSION);
+  visitor.SimulateInFramer(kFrameData, sizeof(kFrameData));
+
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_ERROR, visitor.deframer_.state());
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_INVALID_CONTROL_FRAME_SIZE,
+            visitor.deframer_.spdy_framer_error())
+      << Http2DecoderAdapter::SpdyFramerErrorToString(
+             visitor.deframer_.spdy_framer_error());
+}
+
+// Tests handling of PING frame with incorrect size.
+TEST_P(SpdyFramerTest, ReadIncorrectlySizedPing) {
+  // PING frame of size 4, which isn't correct.
+  const unsigned char kFrameData[] = {
+      0x00, 0x00, 0x04,        // Length: 4
+      0x06,                    //   Type: PING
+      0x00,                    //  Flags: none
+      0x00, 0x00, 0x00, 0x00,  // Stream: 0
+      0x00, 0x00, 0x00, 0x01,  // Ping (Truncated)
+  };
+
+  TestSpdyVisitor visitor(SpdyFramer::DISABLE_COMPRESSION);
+  visitor.SimulateInFramer(kFrameData, sizeof(kFrameData));
+
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_ERROR, visitor.deframer_.state());
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_INVALID_CONTROL_FRAME_SIZE,
+            visitor.deframer_.spdy_framer_error())
+      << Http2DecoderAdapter::SpdyFramerErrorToString(
+             visitor.deframer_.spdy_framer_error());
+}
+
+// Tests handling of WINDOW_UPDATE frame with incorrect size.
+TEST_P(SpdyFramerTest, ReadIncorrectlySizedWindowUpdate) {
+  // WINDOW_UPDATE frame of size 3, which isn't correct.
+  const unsigned char kFrameData[] = {
+      0x00, 0x00, 0x03,        // Length: 3
+      0x08,                    //   Type: WINDOW_UPDATE
+      0x00,                    //  Flags: none
+      0x00, 0x00, 0x00, 0x03,  // Stream: 3
+      0x00, 0x00, 0x01,        // WindowUpdate (Truncated)
+  };
+
+  TestSpdyVisitor visitor(SpdyFramer::DISABLE_COMPRESSION);
+  visitor.SimulateInFramer(kFrameData, sizeof(kFrameData));
+
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_ERROR, visitor.deframer_.state());
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_INVALID_CONTROL_FRAME_SIZE,
+            visitor.deframer_.spdy_framer_error())
+      << Http2DecoderAdapter::SpdyFramerErrorToString(
+             visitor.deframer_.spdy_framer_error());
+}
+
+// Tests handling of RST_STREAM frame with incorrect size.
+TEST_P(SpdyFramerTest, ReadIncorrectlySizedRstStream) {
+  // RST_STREAM frame of size 3, which isn't correct.
+  const unsigned char kFrameData[] = {
+      0x00, 0x00, 0x03,        // Length: 3
+      0x03,                    //   Type: RST_STREAM
+      0x00,                    //  Flags: none
+      0x00, 0x00, 0x00, 0x03,  // Stream: 3
+      0x00, 0x00, 0x01,        // RstStream (Truncated)
+  };
+
+  TestSpdyVisitor visitor(SpdyFramer::DISABLE_COMPRESSION);
+  visitor.SimulateInFramer(kFrameData, sizeof(kFrameData));
+
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_ERROR, visitor.deframer_.state());
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_INVALID_CONTROL_FRAME_SIZE,
+            visitor.deframer_.spdy_framer_error())
+      << Http2DecoderAdapter::SpdyFramerErrorToString(
+             visitor.deframer_.spdy_framer_error());
+}
+
+// Regression test for https://crbug.com/548674:
+// RST_STREAM with payload must not be accepted.
+TEST_P(SpdyFramerTest, ReadInvalidRstStreamWithPayload) {
+  const unsigned char kFrameData[] = {
+      0x00, 0x00, 0x07,        //  Length: 7
+      0x03,                    //    Type: RST_STREAM
+      0x00,                    //   Flags: none
+      0x00, 0x00, 0x00, 0x01,  //  Stream: 1
+      0x00, 0x00, 0x00, 0x00,  //   Error: NO_ERROR
+      'f',  'o',  'o'          // Payload: "foo"
+  };
+
+  TestSpdyVisitor visitor(SpdyFramer::DISABLE_COMPRESSION);
+  visitor.SimulateInFramer(kFrameData, sizeof(kFrameData));
+
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_ERROR, visitor.deframer_.state());
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_INVALID_CONTROL_FRAME_SIZE,
+            visitor.deframer_.spdy_framer_error())
+      << Http2DecoderAdapter::SpdyFramerErrorToString(
+             visitor.deframer_.spdy_framer_error());
+}
+
+// Test that SpdyFramer processes, by default, all passed input in one call
+// to ProcessInput (i.e. will not be calling set_process_single_input_frame()).
+TEST_P(SpdyFramerTest, ProcessAllInput) {
+  auto visitor =
+      SpdyMakeUnique<TestSpdyVisitor>(SpdyFramer::DISABLE_COMPRESSION);
+  deframer_.set_visitor(visitor.get());
+
+  // Create two input frames.
+  SpdyHeadersIR headers(/* stream_id = */ 1);
+  headers.SetHeader("alpha", "beta");
+  headers.SetHeader("gamma", "charlie");
+  headers.SetHeader("cookie", "key1=value1; key2=value2");
+  SpdySerializedFrame headers_frame(SpdyFramerPeer::SerializeHeaders(
+      &framer_, headers, use_output_ ? &output_ : nullptr));
+
+  const char four_score[] = "Four score and seven years ago";
+  SpdyDataIR four_score_ir(/* stream_id = */ 1, four_score);
+  SpdySerializedFrame four_score_frame(framer_.SerializeData(four_score_ir));
+
+  // Put them in a single buffer (new variables here to make it easy to
+  // change the order and type of frames).
+  SpdySerializedFrame frame1 = std::move(headers_frame);
+  SpdySerializedFrame frame2 = std::move(four_score_frame);
+
+  const size_t frame1_size = frame1.size();
+  const size_t frame2_size = frame2.size();
+
+  VLOG(1) << "frame1_size = " << frame1_size;
+  VLOG(1) << "frame2_size = " << frame2_size;
+
+  SpdyString input_buffer;
+  input_buffer.append(frame1.data(), frame1_size);
+  input_buffer.append(frame2.data(), frame2_size);
+
+  const char* buf = input_buffer.data();
+  const size_t buf_size = input_buffer.size();
+
+  VLOG(1) << "buf_size = " << buf_size;
+
+  size_t processed = deframer_.ProcessInput(buf, buf_size);
+  EXPECT_EQ(buf_size, processed);
+  EXPECT_EQ(Http2DecoderAdapter::SPDY_READY_FOR_FRAME, deframer_.state());
+  EXPECT_EQ(1, visitor->headers_frame_count_);
+  EXPECT_EQ(1, visitor->data_frame_count_);
+  EXPECT_EQ(strlen(four_score), static_cast<unsigned>(visitor->data_bytes_));
+}
+
+// Test that SpdyFramer stops after processing a full frame if
+// process_single_input_frame is set. Input to ProcessInput has two frames, but
+// only processes the first when we give it the first frame split at any point,
+// or give it more than one frame in the input buffer.
+TEST_P(SpdyFramerTest, ProcessAtMostOneFrame) {
+  deframer_.set_process_single_input_frame(true);
+
+  // Create two input frames.
+  const char four_score[] = "Four score and ...";
+  SpdyDataIR four_score_ir(/* stream_id = */ 1, four_score);
+  SpdySerializedFrame four_score_frame(framer_.SerializeData(four_score_ir));
+
+  SpdyHeadersIR headers(/* stream_id = */ 2);
+  headers.SetHeader("alpha", "beta");
+  headers.SetHeader("gamma", "charlie");
+  headers.SetHeader("cookie", "key1=value1; key2=value2");
+  SpdySerializedFrame headers_frame(SpdyFramerPeer::SerializeHeaders(
+      &framer_, headers, use_output_ ? &output_ : nullptr));
+
+  // Put them in a single buffer (new variables here to make it easy to
+  // change the order and type of frames).
+  SpdySerializedFrame frame1 = std::move(four_score_frame);
+  SpdySerializedFrame frame2 = std::move(headers_frame);
+
+  const size_t frame1_size = frame1.size();
+  const size_t frame2_size = frame2.size();
+
+  VLOG(1) << "frame1_size = " << frame1_size;
+  VLOG(1) << "frame2_size = " << frame2_size;
+
+  SpdyString input_buffer;
+  input_buffer.append(frame1.data(), frame1_size);
+  input_buffer.append(frame2.data(), frame2_size);
+
+  const char* buf = input_buffer.data();
+  const size_t buf_size = input_buffer.size();
+
+  VLOG(1) << "buf_size = " << buf_size;
+
+  for (size_t first_size = 0; first_size <= buf_size; ++first_size) {
+    VLOG(1) << "first_size = " << first_size;
+    auto visitor =
+        SpdyMakeUnique<TestSpdyVisitor>(SpdyFramer::DISABLE_COMPRESSION);
+    deframer_.set_visitor(visitor.get());
+
+    EXPECT_EQ(Http2DecoderAdapter::SPDY_READY_FOR_FRAME, deframer_.state());
+
+    size_t processed_first = deframer_.ProcessInput(buf, first_size);
+    if (first_size < frame1_size) {
+      EXPECT_EQ(first_size, processed_first);
+
+      if (first_size == 0) {
+        EXPECT_EQ(Http2DecoderAdapter::SPDY_READY_FOR_FRAME, deframer_.state());
+      } else {
+        EXPECT_NE(Http2DecoderAdapter::SPDY_READY_FOR_FRAME, deframer_.state());
+      }
+
+      const char* rest = buf + processed_first;
+      const size_t remaining = buf_size - processed_first;
+      VLOG(1) << "remaining = " << remaining;
+
+      size_t processed_second = deframer_.ProcessInput(rest, remaining);
+
+      // Redundant tests just to make it easier to think about.
+      EXPECT_EQ(frame1_size - processed_first, processed_second);
+      size_t processed_total = processed_first + processed_second;
+      EXPECT_EQ(frame1_size, processed_total);
+    } else {
+      EXPECT_EQ(frame1_size, processed_first);
+    }
+
+    EXPECT_EQ(Http2DecoderAdapter::SPDY_READY_FOR_FRAME, deframer_.state());
+
+    // At this point should have processed the entirety of the first frame,
+    // and none of the second frame.
+
+    EXPECT_EQ(1, visitor->data_frame_count_);
+    EXPECT_EQ(strlen(four_score), static_cast<unsigned>(visitor->data_bytes_));
+    EXPECT_EQ(0, visitor->headers_frame_count_);
+  }
+}
+
+namespace {
+void CheckFrameAndIRSize(SpdyFrameIR* ir,
+                         SpdyFramer* framer,
+                         ArrayOutputBuffer* output_buffer) {
+  output_buffer->Reset();
+  SpdyFrameType type = ir->frame_type();
+  size_t ir_size = ir->size();
+  framer->SerializeFrame(*ir, output_buffer);
+  if (type == SpdyFrameType::HEADERS || type == SpdyFrameType::PUSH_PROMISE) {
+    // For HEADERS and PUSH_PROMISE, the size is an estimate.
+    EXPECT_GE(ir_size, output_buffer->Size() * 9 / 10);
+    EXPECT_LT(ir_size, output_buffer->Size() * 11 / 10);
+  } else {
+    EXPECT_EQ(ir_size, output_buffer->Size());
+  }
+}
+}  // namespace
+
+TEST_P(SpdyFramerTest, SpdyFrameIRSize) {
+  SpdyFramer framer(SpdyFramer::DISABLE_COMPRESSION);
+
+  const char bytes[] = "this is a very short data frame";
+  SpdyDataIR data_ir(1, SpdyStringPiece(bytes, SPDY_ARRAYSIZE(bytes)));
+  CheckFrameAndIRSize(&data_ir, &framer, &output_);
+
+  SpdyRstStreamIR rst_ir(/* stream_id = */ 1, ERROR_CODE_PROTOCOL_ERROR);
+  CheckFrameAndIRSize(&rst_ir, &framer, &output_);
+
+  SpdySettingsIR settings_ir;
+  settings_ir.AddSetting(SETTINGS_HEADER_TABLE_SIZE, 5);
+  settings_ir.AddSetting(SETTINGS_ENABLE_PUSH, 6);
+  settings_ir.AddSetting(SETTINGS_MAX_CONCURRENT_STREAMS, 7);
+  CheckFrameAndIRSize(&settings_ir, &framer, &output_);
+
+  SpdyPingIR ping_ir(42);
+  CheckFrameAndIRSize(&ping_ir, &framer, &output_);
+
+  SpdyGoAwayIR goaway_ir(97, ERROR_CODE_NO_ERROR, "Goaway description");
+  CheckFrameAndIRSize(&goaway_ir, &framer, &output_);
+
+  SpdyHeadersIR headers_ir(1);
+  headers_ir.SetHeader("alpha", "beta");
+  headers_ir.SetHeader("gamma", "charlie");
+  headers_ir.SetHeader("cookie", "key1=value1; key2=value2");
+  CheckFrameAndIRSize(&headers_ir, &framer, &output_);
+
+  SpdyHeadersIR headers_ir_with_continuation(1);
+  headers_ir_with_continuation.SetHeader("alpha", SpdyString(100000, 'x'));
+  headers_ir_with_continuation.SetHeader("beta", SpdyString(100000, 'x'));
+  headers_ir_with_continuation.SetHeader("cookie", "key1=value1; key2=value2");
+  CheckFrameAndIRSize(&headers_ir_with_continuation, &framer, &output_);
+
+  SpdyWindowUpdateIR window_update_ir(4, 1024);
+  CheckFrameAndIRSize(&window_update_ir, &framer, &output_);
+
+  SpdyPushPromiseIR push_promise_ir(3, 8);
+  push_promise_ir.SetHeader("alpha", SpdyString(100000, 'x'));
+  push_promise_ir.SetHeader("beta", SpdyString(100000, 'x'));
+  push_promise_ir.SetHeader("cookie", "key1=value1; key2=value2");
+  CheckFrameAndIRSize(&push_promise_ir, &framer, &output_);
+
+  SpdyAltSvcWireFormat::AlternativeService altsvc1(
+      "pid1", "host", 443, 5, SpdyAltSvcWireFormat::VersionVector());
+  SpdyAltSvcWireFormat::AlternativeService altsvc2(
+      "p\"=i:d", "h_\\o\"st", 123, 42, SpdyAltSvcWireFormat::VersionVector{24});
+  SpdyAltSvcWireFormat::AlternativeServiceVector altsvc_vector;
+  altsvc_vector.push_back(altsvc1);
+  altsvc_vector.push_back(altsvc2);
+  SpdyAltSvcIR altsvc_ir(0);
+  altsvc_ir.set_origin("o_r|g!n");
+  altsvc_ir.add_altsvc(altsvc1);
+  altsvc_ir.add_altsvc(altsvc2);
+  CheckFrameAndIRSize(&altsvc_ir, &framer, &output_);
+
+  SpdyPriorityIR priority_ir(3, 1, 256, false);
+  CheckFrameAndIRSize(&priority_ir, &framer, &output_);
+
+  const char kDescription[] = "Unknown frame";
+  const uint8_t kType = 0xaf;
+  const uint8_t kFlags = 0x11;
+  SpdyUnknownIR unknown_ir(2, kType, kFlags, kDescription);
+  CheckFrameAndIRSize(&unknown_ir, &framer, &output_);
+}
+
+}  // namespace test
+
+}  // namespace spdy
diff --git a/spdy/core/spdy_header_block.cc b/spdy/core/spdy_header_block.cc
new file mode 100644
index 0000000..dcf84b9
--- /dev/null
+++ b/spdy/core/spdy_header_block.cc
@@ -0,0 +1,401 @@
+// Copyright (c) 2012 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "net/third_party/quiche/src/spdy/core/spdy_header_block.h"
+
+#include <string.h>
+
+#include <algorithm>
+#include <utility>
+
+#include "base/logging.h"
+#include "base/macros.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_estimate_memory_usage.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_ptr_util.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string_utils.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_unsafe_arena.h"
+
+namespace spdy {
+namespace {
+
+// By default, linked_hash_map's internal map allocates space for 100 map
+// buckets on construction, which is larger than necessary.  Standard library
+// unordered map implementations use a list of prime numbers to set the bucket
+// count for a particular capacity.  |kInitialMapBuckets| is chosen to reduce
+// memory usage for small header blocks, at the cost of having to rehash for
+// large header blocks.
+const size_t kInitialMapBuckets = 11;
+
+// SpdyHeaderBlock::Storage allocates blocks of this size by default.
+const size_t kDefaultStorageBlockSize = 2048;
+
+const char kCookieKey[] = "cookie";
+const char kNullSeparator = 0;
+
+SpdyStringPiece SeparatorForKey(SpdyStringPiece key) {
+  if (key == kCookieKey) {
+    static SpdyStringPiece cookie_separator = "; ";
+    return cookie_separator;
+  } else {
+    return SpdyStringPiece(&kNullSeparator, 1);
+  }
+}
+
+}  // namespace
+
+// This class provides a backing store for SpdyStringPieces. It previously used
+// custom allocation logic, but now uses an UnsafeArena instead. It has the
+// property that SpdyStringPieces that refer to data in Storage are never
+// invalidated until the Storage is deleted or Clear() is called.
+//
+// Write operations always append to the last block. If there is not enough
+// space to perform the write, a new block is allocated, and any unused space
+// is wasted.
+class SpdyHeaderBlock::Storage {
+ public:
+  Storage() : arena_(kDefaultStorageBlockSize) {}
+  Storage(const Storage&) = delete;
+  Storage& operator=(const Storage&) = delete;
+
+  SpdyStringPiece Write(const SpdyStringPiece s) {
+    return SpdyStringPiece(arena_.Memdup(s.data(), s.size()), s.size());
+  }
+
+  // If |s| points to the most recent allocation from arena_, the arena will
+  // reclaim the memory. Otherwise, this method is a no-op.
+  void Rewind(const SpdyStringPiece s) {
+    arena_.Free(const_cast<char*>(s.data()), s.size());
+  }
+
+  void Clear() { arena_.Reset(); }
+
+  // Given a list of fragments and a separator, writes the fragments joined by
+  // the separator to a contiguous region of memory. Returns a SpdyStringPiece
+  // pointing to the region of memory.
+  SpdyStringPiece WriteFragments(const std::vector<SpdyStringPiece>& fragments,
+                                 SpdyStringPiece separator) {
+    if (fragments.empty()) {
+      return SpdyStringPiece();
+    }
+    size_t total_size = separator.size() * (fragments.size() - 1);
+    for (const auto fragment : fragments) {
+      total_size += fragment.size();
+    }
+    char* dst = arena_.Alloc(total_size);
+    size_t written = Join(dst, fragments, separator);
+    DCHECK_EQ(written, total_size);
+    return SpdyStringPiece(dst, total_size);
+  }
+
+  size_t bytes_allocated() const { return arena_.status().bytes_allocated(); }
+
+  // TODO(xunjieli): https://crbug.com/669108. Merge this with bytes_allocated()
+  size_t EstimateMemoryUsage() const {
+    return arena_.status().bytes_allocated();
+  }
+
+ private:
+  SpdyUnsafeArena arena_;
+};
+
+SpdyHeaderBlock::HeaderValue::HeaderValue(Storage* storage,
+                                          SpdyStringPiece key,
+                                          SpdyStringPiece initial_value)
+    : storage_(storage),
+      fragments_({initial_value}),
+      pair_({key, {}}),
+      size_(initial_value.size()),
+      separator_size_(SeparatorForKey(key).size()) {}
+
+SpdyHeaderBlock::HeaderValue::HeaderValue(HeaderValue&& other)
+    : storage_(other.storage_),
+      fragments_(std::move(other.fragments_)),
+      pair_(std::move(other.pair_)),
+      size_(other.size_),
+      separator_size_(other.separator_size_) {}
+
+SpdyHeaderBlock::HeaderValue& SpdyHeaderBlock::HeaderValue::operator=(
+    HeaderValue&& other) {
+  storage_ = other.storage_;
+  fragments_ = std::move(other.fragments_);
+  pair_ = std::move(other.pair_);
+  size_ = other.size_;
+  separator_size_ = other.separator_size_;
+  return *this;
+}
+
+SpdyHeaderBlock::HeaderValue::~HeaderValue() = default;
+
+SpdyStringPiece SpdyHeaderBlock::HeaderValue::ConsolidatedValue() const {
+  if (fragments_.empty()) {
+    return SpdyStringPiece();
+  }
+  if (fragments_.size() > 1) {
+    fragments_ = {
+        storage_->WriteFragments(fragments_, SeparatorForKey(pair_.first))};
+  }
+  return fragments_[0];
+}
+
+void SpdyHeaderBlock::HeaderValue::Append(SpdyStringPiece fragment) {
+  size_ += (fragment.size() + separator_size_);
+  fragments_.push_back(fragment);
+}
+
+const std::pair<SpdyStringPiece, SpdyStringPiece>&
+SpdyHeaderBlock::HeaderValue::as_pair() const {
+  pair_.second = ConsolidatedValue();
+  return pair_;
+}
+
+SpdyHeaderBlock::iterator::iterator(MapType::const_iterator it) : it_(it) {}
+
+SpdyHeaderBlock::iterator::iterator(const iterator& other) = default;
+
+SpdyHeaderBlock::iterator::~iterator() = default;
+
+SpdyHeaderBlock::ValueProxy::ValueProxy(
+    SpdyHeaderBlock::MapType* block,
+    SpdyHeaderBlock::Storage* storage,
+    SpdyHeaderBlock::MapType::iterator lookup_result,
+    const SpdyStringPiece key,
+    size_t* spdy_header_block_value_size)
+    : block_(block),
+      storage_(storage),
+      lookup_result_(lookup_result),
+      key_(key),
+      spdy_header_block_value_size_(spdy_header_block_value_size),
+      valid_(true) {}
+
+SpdyHeaderBlock::ValueProxy::ValueProxy(ValueProxy&& other)
+    : block_(other.block_),
+      storage_(other.storage_),
+      lookup_result_(other.lookup_result_),
+      key_(other.key_),
+      spdy_header_block_value_size_(other.spdy_header_block_value_size_),
+      valid_(true) {
+  other.valid_ = false;
+}
+
+SpdyHeaderBlock::ValueProxy& SpdyHeaderBlock::ValueProxy::operator=(
+    SpdyHeaderBlock::ValueProxy&& other) {
+  block_ = other.block_;
+  storage_ = other.storage_;
+  lookup_result_ = other.lookup_result_;
+  key_ = other.key_;
+  valid_ = true;
+  other.valid_ = false;
+  spdy_header_block_value_size_ = other.spdy_header_block_value_size_;
+  return *this;
+}
+
+SpdyHeaderBlock::ValueProxy::~ValueProxy() {
+  // If the ValueProxy is destroyed while lookup_result_ == block_->end(),
+  // the assignment operator was never used, and the block's Storage can
+  // reclaim the memory used by the key. This makes lookup-only access to
+  // SpdyHeaderBlock through operator[] memory-neutral.
+  if (valid_ && lookup_result_ == block_->end()) {
+    storage_->Rewind(key_);
+  }
+}
+
+SpdyHeaderBlock::ValueProxy& SpdyHeaderBlock::ValueProxy::operator=(
+    const SpdyStringPiece value) {
+  *spdy_header_block_value_size_ += value.size();
+  if (lookup_result_ == block_->end()) {
+    DVLOG(1) << "Inserting: (" << key_ << ", " << value << ")";
+    lookup_result_ =
+        block_
+            ->emplace(std::make_pair(
+                key_, HeaderValue(storage_, key_, storage_->Write(value))))
+            .first;
+  } else {
+    DVLOG(1) << "Updating key: " << key_ << " with value: " << value;
+    *spdy_header_block_value_size_ -= lookup_result_->second.SizeEstimate();
+    lookup_result_->second =
+        HeaderValue(storage_, key_, storage_->Write(value));
+  }
+  return *this;
+}
+
+SpdyString SpdyHeaderBlock::ValueProxy::as_string() const {
+  if (lookup_result_ == block_->end()) {
+    return "";
+  } else {
+    return SpdyString(lookup_result_->second.value());
+  }
+}
+
+SpdyHeaderBlock::SpdyHeaderBlock() : block_(kInitialMapBuckets) {}
+
+SpdyHeaderBlock::SpdyHeaderBlock(SpdyHeaderBlock&& other)
+    : block_(kInitialMapBuckets) {
+  block_.swap(other.block_);
+  storage_.swap(other.storage_);
+  key_size_ = other.key_size_;
+  value_size_ = other.value_size_;
+}
+
+SpdyHeaderBlock::~SpdyHeaderBlock() = default;
+
+SpdyHeaderBlock& SpdyHeaderBlock::operator=(SpdyHeaderBlock&& other) {
+  block_.swap(other.block_);
+  storage_.swap(other.storage_);
+  key_size_ = other.key_size_;
+  value_size_ = other.value_size_;
+  return *this;
+}
+
+SpdyHeaderBlock SpdyHeaderBlock::Clone() const {
+  SpdyHeaderBlock copy;
+  for (const auto& p : *this) {
+    copy.AppendHeader(p.first, p.second);
+  }
+  return copy;
+}
+
+bool SpdyHeaderBlock::operator==(const SpdyHeaderBlock& other) const {
+  return size() == other.size() && std::equal(begin(), end(), other.begin());
+}
+
+bool SpdyHeaderBlock::operator!=(const SpdyHeaderBlock& other) const {
+  return !(operator==(other));
+}
+
+SpdyString SpdyHeaderBlock::DebugString() const {
+  if (empty()) {
+    return "{}";
+  }
+
+  SpdyString output = "\n{\n";
+  for (auto it = begin(); it != end(); ++it) {
+    SpdyStrAppend(&output, "  ", it->first, " ", it->second, "\n");
+  }
+  SpdyStrAppend(&output, "}\n");
+  return output;
+}
+
+void SpdyHeaderBlock::erase(SpdyStringPiece key) {
+  auto iter = block_.find(key);
+  if (iter != block_.end()) {
+    DVLOG(1) << "Erasing header with name: " << key;
+    key_size_ -= key.size();
+    value_size_ -= iter->second.SizeEstimate();
+    block_.erase(iter);
+  }
+}
+
+void SpdyHeaderBlock::clear() {
+  key_size_ = 0;
+  value_size_ = 0;
+  block_.clear();
+  storage_.reset();
+}
+
+void SpdyHeaderBlock::insert(const SpdyHeaderBlock::value_type& value) {
+  // TODO(birenroy): Write new value in place of old value, if it fits.
+  value_size_ += value.second.size();
+
+  auto iter = block_.find(value.first);
+  if (iter == block_.end()) {
+    DVLOG(1) << "Inserting: (" << value.first << ", " << value.second << ")";
+    AppendHeader(value.first, value.second);
+  } else {
+    DVLOG(1) << "Updating key: " << iter->first
+             << " with value: " << value.second;
+    value_size_ -= iter->second.SizeEstimate();
+    auto* storage = GetStorage();
+    iter->second =
+        HeaderValue(storage, iter->first, storage->Write(value.second));
+  }
+}
+
+SpdyHeaderBlock::ValueProxy SpdyHeaderBlock::operator[](
+    const SpdyStringPiece key) {
+  DVLOG(2) << "Operator[] saw key: " << key;
+  SpdyStringPiece out_key;
+  auto iter = block_.find(key);
+  if (iter == block_.end()) {
+    // We write the key first, to assure that the ValueProxy has a
+    // reference to a valid SpdyStringPiece in its operator=.
+    out_key = WriteKey(key);
+    DVLOG(2) << "Key written as: " << std::hex
+             << static_cast<const void*>(key.data()) << ", " << std::dec
+             << key.size();
+  } else {
+    out_key = iter->first;
+  }
+  return ValueProxy(&block_, GetStorage(), iter, out_key, &value_size_);
+}
+
+void SpdyHeaderBlock::AppendValueOrAddHeader(const SpdyStringPiece key,
+                                             const SpdyStringPiece value) {
+  value_size_ += value.size();
+
+  auto iter = block_.find(key);
+  if (iter == block_.end()) {
+    DVLOG(1) << "Inserting: (" << key << ", " << value << ")";
+
+    AppendHeader(key, value);
+    return;
+  }
+  DVLOG(1) << "Updating key: " << iter->first << "; appending value: " << value;
+  value_size_ += SeparatorForKey(key).size();
+  iter->second.Append(GetStorage()->Write(value));
+}
+
+size_t SpdyHeaderBlock::EstimateMemoryUsage() const {
+  // TODO(xunjieli): https://crbug.com/669108. Also include |block_| when EMU()
+  // supports linked_hash_map.
+  return SpdyEstimateMemoryUsage(storage_);
+}
+
+void SpdyHeaderBlock::AppendHeader(const SpdyStringPiece key,
+                                   const SpdyStringPiece value) {
+  auto backed_key = WriteKey(key);
+  auto* storage = GetStorage();
+  block_.emplace(std::make_pair(
+      backed_key, HeaderValue(storage, backed_key, storage->Write(value))));
+}
+
+SpdyHeaderBlock::Storage* SpdyHeaderBlock::GetStorage() {
+  if (storage_ == nullptr) {
+    storage_ = SpdyMakeUnique<Storage>();
+  }
+  return storage_.get();
+}
+
+SpdyStringPiece SpdyHeaderBlock::WriteKey(const SpdyStringPiece key) {
+  key_size_ += key.size();
+  return GetStorage()->Write(key);
+}
+
+size_t SpdyHeaderBlock::bytes_allocated() const {
+  if (storage_ == nullptr) {
+    return 0;
+  } else {
+    return storage_->bytes_allocated();
+  }
+}
+
+size_t Join(char* dst,
+            const std::vector<SpdyStringPiece>& fragments,
+            SpdyStringPiece separator) {
+  if (fragments.empty()) {
+    return 0;
+  }
+  auto* original_dst = dst;
+  auto it = fragments.begin();
+  memcpy(dst, it->data(), it->size());
+  dst += it->size();
+  for (++it; it != fragments.end(); ++it) {
+    memcpy(dst, separator.data(), separator.size());
+    dst += separator.size();
+    memcpy(dst, it->data(), it->size());
+    dst += it->size();
+  }
+  return dst - original_dst;
+}
+
+}  // namespace spdy
diff --git a/spdy/core/spdy_header_block.h b/spdy/core/spdy_header_block.h
new file mode 100644
index 0000000..f453246
--- /dev/null
+++ b/spdy/core/spdy_header_block.h
@@ -0,0 +1,254 @@
+// Copyright (c) 2012 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef QUICHE_SPDY_CORE_SPDY_HEADER_BLOCK_H_
+#define QUICHE_SPDY_CORE_SPDY_HEADER_BLOCK_H_
+
+#include <stddef.h>
+
+#include <list>
+#include <memory>
+#include <utility>
+#include <vector>
+
+#include "base/macros.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_containers.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_export.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_macros.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string_piece.h"
+
+namespace spdy {
+
+namespace test {
+class SpdyHeaderBlockPeer;
+class ValueProxyPeer;
+}  // namespace test
+
+// This class provides a key-value map that can be used to store SPDY header
+// names and values. This data structure preserves insertion order.
+//
+// Under the hood, this data structure uses large, contiguous blocks of memory
+// to store names and values. Lookups may be performed with SpdyStringPiece
+// keys, and values are returned as SpdyStringPieces (via ValueProxy, below).
+// Value SpdyStringPieces are valid as long as the SpdyHeaderBlock exists;
+// allocated memory is never freed until SpdyHeaderBlock's destruction.
+//
+// This implementation does not make much of an effort to minimize wasted space.
+// It's expected that keys are rarely deleted from a SpdyHeaderBlock.
+class SPDY_EXPORT_PRIVATE SpdyHeaderBlock {
+ private:
+  class Storage;
+
+  // Stores a list of value fragments that can be joined later with a
+  // key-dependent separator.
+  class SPDY_EXPORT_PRIVATE HeaderValue {
+   public:
+    HeaderValue(Storage* storage,
+                SpdyStringPiece key,
+                SpdyStringPiece initial_value);
+
+    // Moves are allowed.
+    HeaderValue(HeaderValue&& other);
+    HeaderValue& operator=(HeaderValue&& other);
+
+    // Copies are not.
+    HeaderValue(const HeaderValue& other) = delete;
+    HeaderValue& operator=(const HeaderValue& other) = delete;
+
+    ~HeaderValue();
+
+    // Consumes at most |fragment.size()| bytes of memory.
+    void Append(SpdyStringPiece fragment);
+
+    SpdyStringPiece value() const { return as_pair().second; }
+    const std::pair<SpdyStringPiece, SpdyStringPiece>& as_pair() const;
+
+    // Size estimate including separators. Used when keys are erased from
+    // SpdyHeaderBlock.
+    size_t SizeEstimate() const { return size_; }
+
+   private:
+    // May allocate a large contiguous region of memory to hold the concatenated
+    // fragments and separators.
+    SpdyStringPiece ConsolidatedValue() const;
+
+    mutable Storage* storage_;
+    mutable std::vector<SpdyStringPiece> fragments_;
+    // The first element is the key; the second is the consolidated value.
+    mutable std::pair<SpdyStringPiece, SpdyStringPiece> pair_;
+    size_t size_ = 0;
+    size_t separator_size_ = 0;
+  };
+
+  typedef SpdyLinkedHashMap<SpdyStringPiece, HeaderValue, SpdyStringPieceHash>
+      MapType;
+
+ public:
+  typedef std::pair<SpdyStringPiece, SpdyStringPiece> value_type;
+
+  // Provides iteration over a sequence of std::pair<SpdyStringPiece,
+  // SpdyStringPiece>, even though the underlying MapType::value_type is
+  // different. Dereferencing the iterator will result in memory allocation for
+  // multi-value headers.
+  class SPDY_EXPORT_PRIVATE iterator {
+   public:
+    // The following type definitions fulfill the requirements for iterator
+    // implementations.
+    typedef std::pair<SpdyStringPiece, SpdyStringPiece> value_type;
+    typedef value_type& reference;
+    typedef value_type* pointer;
+    typedef std::forward_iterator_tag iterator_category;
+    typedef MapType::iterator::difference_type difference_type;
+
+    // In practice, this iterator only offers access to const value_type.
+    typedef const value_type& const_reference;
+    typedef const value_type* const_pointer;
+
+    explicit iterator(MapType::const_iterator it);
+    iterator(const iterator& other);
+    ~iterator();
+
+    // This will result in memory allocation if the value consists of multiple
+    // fragments.
+    const_reference operator*() const { return it_->second.as_pair(); }
+
+    const_pointer operator->() const { return &(this->operator*()); }
+    bool operator==(const iterator& it) const { return it_ == it.it_; }
+    bool operator!=(const iterator& it) const { return !(*this == it); }
+
+    iterator& operator++() {
+      it_++;
+      return *this;
+    }
+
+    iterator operator++(int) {
+      auto ret = *this;
+      this->operator++();
+      return ret;
+    }
+
+   private:
+    MapType::const_iterator it_;
+  };
+  typedef iterator const_iterator;
+
+  class ValueProxy;
+
+  SpdyHeaderBlock();
+  SpdyHeaderBlock(const SpdyHeaderBlock& other) = delete;
+  SpdyHeaderBlock(SpdyHeaderBlock&& other);
+  ~SpdyHeaderBlock();
+
+  SpdyHeaderBlock& operator=(const SpdyHeaderBlock& other) = delete;
+  SpdyHeaderBlock& operator=(SpdyHeaderBlock&& other);
+  SpdyHeaderBlock Clone() const;
+
+  bool operator==(const SpdyHeaderBlock& other) const;
+  bool operator!=(const SpdyHeaderBlock& other) const;
+
+  // Provides a human readable multi-line representation of the stored header
+  // keys and values.
+  SpdyString DebugString() const;
+
+  iterator begin() { return iterator(block_.begin()); }
+  iterator end() { return iterator(block_.end()); }
+  const_iterator begin() const { return const_iterator(block_.begin()); }
+  const_iterator end() const { return const_iterator(block_.end()); }
+  bool empty() const { return block_.empty(); }
+  size_t size() const { return block_.size(); }
+  iterator find(SpdyStringPiece key) { return iterator(block_.find(key)); }
+  const_iterator find(SpdyStringPiece key) const {
+    return const_iterator(block_.find(key));
+  }
+  void erase(SpdyStringPiece key);
+
+  // Clears both our MapType member and the memory used to hold headers.
+  void clear();
+
+  // The next few methods copy data into our backing storage.
+
+  // If key already exists in the block, replaces the value of that key. Else
+  // adds a new header to the end of the block.
+  void insert(const value_type& value);
+
+  // If a header with the key is already present, then append the value to the
+  // existing header value, NUL ("\0") separated unless the key is cookie, in
+  // which case the separator is "; ".
+  // If there is no such key, a new header with the key and value is added.
+  void AppendValueOrAddHeader(const SpdyStringPiece key,
+                              const SpdyStringPiece value);
+
+  // Allows either lookup or mutation of the value associated with a key.
+  ValueProxy operator[](const SpdyStringPiece key) SPDY_MUST_USE_RESULT;
+
+  // This object provides automatic conversions that allow SpdyHeaderBlock to be
+  // nearly a drop-in replacement for SpdyLinkedHashMap<SpdyString, SpdyString>.
+  // It reads data from or writes data to a SpdyHeaderBlock::Storage.
+  class SPDY_EXPORT_PRIVATE ValueProxy {
+   public:
+    ~ValueProxy();
+
+    // Moves are allowed.
+    ValueProxy(ValueProxy&& other);
+    ValueProxy& operator=(ValueProxy&& other);
+
+    // Copies are not.
+    ValueProxy(const ValueProxy& other) = delete;
+    ValueProxy& operator=(const ValueProxy& other) = delete;
+
+    // Assignment modifies the underlying SpdyHeaderBlock.
+    ValueProxy& operator=(const SpdyStringPiece other);
+
+    SpdyString as_string() const;
+
+   private:
+    friend class SpdyHeaderBlock;
+    friend class test::ValueProxyPeer;
+
+    ValueProxy(SpdyHeaderBlock::MapType* block,
+               SpdyHeaderBlock::Storage* storage,
+               SpdyHeaderBlock::MapType::iterator lookup_result,
+               const SpdyStringPiece key,
+               size_t* spdy_header_block_value_size);
+
+    SpdyHeaderBlock::MapType* block_;
+    SpdyHeaderBlock::Storage* storage_;
+    SpdyHeaderBlock::MapType::iterator lookup_result_;
+    SpdyStringPiece key_;
+    size_t* spdy_header_block_value_size_;
+    bool valid_;
+  };
+
+  // Returns the estimate of dynamically allocated memory in bytes.
+  size_t EstimateMemoryUsage() const;
+
+  size_t TotalBytesUsed() const { return key_size_ + value_size_; }
+
+ private:
+  friend class test::SpdyHeaderBlockPeer;
+
+  void AppendHeader(const SpdyStringPiece key, const SpdyStringPiece value);
+  Storage* GetStorage();
+  SpdyStringPiece WriteKey(const SpdyStringPiece key);
+  size_t bytes_allocated() const;
+
+  // SpdyStringPieces held by |block_| point to memory owned by |*storage_|.
+  // |storage_| might be nullptr as long as |block_| is empty.
+  MapType block_;
+  std::unique_ptr<Storage> storage_;
+
+  size_t key_size_ = 0;
+  size_t value_size_ = 0;
+};
+
+// Writes |fragments| to |dst|, joined by |separator|. |dst| must be large
+// enough to hold the result. Returns the number of bytes written.
+SPDY_EXPORT_PRIVATE size_t Join(char* dst,
+                                const std::vector<SpdyStringPiece>& fragments,
+                                SpdyStringPiece separator);
+
+}  // namespace spdy
+
+#endif  // QUICHE_SPDY_CORE_SPDY_HEADER_BLOCK_H_
diff --git a/spdy/core/spdy_header_block_test.cc b/spdy/core/spdy_header_block_test.cc
new file mode 100644
index 0000000..3511a21
--- /dev/null
+++ b/spdy/core/spdy_header_block_test.cc
@@ -0,0 +1,252 @@
+// Copyright (c) 2012 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "net/third_party/quiche/src/spdy/core/spdy_header_block.h"
+
+#include <memory>
+#include <utility>
+
+#include "testing/gmock/include/gmock/gmock.h"
+#include "testing/gtest/include/gtest/gtest.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_test_utils.h"
+
+using ::testing::ElementsAre;
+
+namespace spdy {
+namespace test {
+
+class ValueProxyPeer {
+ public:
+  static SpdyStringPiece key(SpdyHeaderBlock::ValueProxy* p) { return p->key_; }
+};
+
+std::pair<SpdyStringPiece, SpdyStringPiece> Pair(SpdyStringPiece k,
+                                                 SpdyStringPiece v) {
+  return std::make_pair(k, v);
+}
+
+// This test verifies that SpdyHeaderBlock behaves correctly when empty.
+TEST(SpdyHeaderBlockTest, EmptyBlock) {
+  SpdyHeaderBlock block;
+  EXPECT_TRUE(block.empty());
+  EXPECT_EQ(0u, block.size());
+  EXPECT_EQ(block.end(), block.find("foo"));
+  EXPECT_TRUE(block.end() == block.begin());
+
+  // Should have no effect.
+  block.erase("bar");
+}
+
+TEST(SpdyHeaderBlockTest, KeyMemoryReclaimedOnLookup) {
+  SpdyHeaderBlock block;
+  SpdyStringPiece copied_key1;
+  {
+    auto proxy1 = block["some key name"];
+    copied_key1 = ValueProxyPeer::key(&proxy1);
+  }
+  SpdyStringPiece copied_key2;
+  {
+    auto proxy2 = block["some other key name"];
+    copied_key2 = ValueProxyPeer::key(&proxy2);
+  }
+  // Because proxy1 was never used to modify the block, the memory used for the
+  // key could be reclaimed and used for the second call to operator[].
+  // Therefore, we expect the pointers of the two SpdyStringPieces to be equal.
+  EXPECT_EQ(copied_key1.data(), copied_key2.data());
+
+  {
+    auto proxy1 = block["some key name"];
+    block["some other key name"] = "some value";
+  }
+  // Nothing should blow up when proxy1 is destructed, and we should be able to
+  // modify and access the SpdyHeaderBlock.
+  block["key"] = "value";
+  EXPECT_EQ("value", block["key"]);
+  EXPECT_EQ("some value", block["some other key name"]);
+  EXPECT_TRUE(block.find("some key name") == block.end());
+}
+
+// This test verifies that headers can be set in a variety of ways.
+TEST(SpdyHeaderBlockTest, AddHeaders) {
+  SpdyHeaderBlock block;
+  block["foo"] = SpdyString(300, 'x');
+  block["bar"] = "baz";
+  block["qux"] = "qux1";
+  block["qux"] = "qux2";
+  block.insert(std::make_pair("key", "value"));
+
+  EXPECT_EQ(Pair("foo", SpdyString(300, 'x')), *block.find("foo"));
+  EXPECT_EQ("baz", block["bar"]);
+  SpdyString qux("qux");
+  EXPECT_EQ("qux2", block[qux]);
+  ASSERT_NE(block.end(), block.find("key"));
+  EXPECT_EQ(Pair("key", "value"), *block.find("key"));
+
+  block.erase("key");
+  EXPECT_EQ(block.end(), block.find("key"));
+}
+
+// This test verifies that SpdyHeaderBlock can be copied using Clone().
+TEST(SpdyHeaderBlockTest, CopyBlocks) {
+  SpdyHeaderBlock block1;
+  block1["foo"] = SpdyString(300, 'x');
+  block1["bar"] = "baz";
+  block1.insert(std::make_pair("qux", "qux1"));
+
+  SpdyHeaderBlock block2 = block1.Clone();
+  SpdyHeaderBlock block3(block1.Clone());
+
+  EXPECT_EQ(block1, block2);
+  EXPECT_EQ(block1, block3);
+}
+
+TEST(SpdyHeaderBlockTest, Equality) {
+  // Test equality and inequality operators.
+  SpdyHeaderBlock block1;
+  block1["foo"] = "bar";
+
+  SpdyHeaderBlock block2;
+  block2["foo"] = "bar";
+
+  SpdyHeaderBlock block3;
+  block3["baz"] = "qux";
+
+  EXPECT_EQ(block1, block2);
+  EXPECT_NE(block1, block3);
+
+  block2["baz"] = "qux";
+  EXPECT_NE(block1, block2);
+}
+
+// Test that certain methods do not crash on moved-from instances.
+TEST(SpdyHeaderBlockTest, MovedFromIsValid) {
+  SpdyHeaderBlock block1;
+  block1["foo"] = "bar";
+
+  SpdyHeaderBlock block2(std::move(block1));
+  EXPECT_THAT(block2, ElementsAre(Pair("foo", "bar")));
+
+  block1["baz"] = "qux";  // NOLINT  testing post-move behavior
+
+  SpdyHeaderBlock block3(std::move(block1));
+
+  block1["foo"] = "bar";  // NOLINT  testing post-move behavior
+
+  SpdyHeaderBlock block4(std::move(block1));
+
+  block1.clear();  // NOLINT  testing post-move behavior
+  EXPECT_TRUE(block1.empty());
+
+  block1["foo"] = "bar";
+  EXPECT_THAT(block1, ElementsAre(Pair("foo", "bar")));
+}
+
+// This test verifies that headers can be appended to no matter how they were
+// added originally.
+TEST(SpdyHeaderBlockTest, AppendHeaders) {
+  SpdyHeaderBlock block;
+  block["foo"] = "foo";
+  block.AppendValueOrAddHeader("foo", "bar");
+  EXPECT_EQ(Pair("foo", SpdyString("foo\0bar", 7)), *block.find("foo"));
+
+  block.insert(std::make_pair("foo", "baz"));
+  EXPECT_EQ("baz", block["foo"]);
+  EXPECT_EQ(Pair("foo", "baz"), *block.find("foo"));
+
+  // Try all four methods of adding an entry.
+  block["cookie"] = "key1=value1";
+  block.AppendValueOrAddHeader("h1", "h1v1");
+  block.insert(std::make_pair("h2", "h2v1"));
+
+  block.AppendValueOrAddHeader("h3", "h3v2");
+  block.AppendValueOrAddHeader("h2", "h2v2");
+  block.AppendValueOrAddHeader("h1", "h1v2");
+  block.AppendValueOrAddHeader("cookie", "key2=value2");
+
+  block.AppendValueOrAddHeader("cookie", "key3=value3");
+  block.AppendValueOrAddHeader("h1", "h1v3");
+  block.AppendValueOrAddHeader("h2", "h2v3");
+  block.AppendValueOrAddHeader("h3", "h3v3");
+  block.AppendValueOrAddHeader("h4", "singleton");
+
+  EXPECT_EQ("key1=value1; key2=value2; key3=value3", block["cookie"]);
+  EXPECT_EQ("baz", block["foo"]);
+  EXPECT_EQ(SpdyString("h1v1\0h1v2\0h1v3", 14), block["h1"]);
+  EXPECT_EQ(SpdyString("h2v1\0h2v2\0h2v3", 14), block["h2"]);
+  EXPECT_EQ(SpdyString("h3v2\0h3v3", 9), block["h3"]);
+  EXPECT_EQ("singleton", block["h4"]);
+}
+
+TEST(JoinTest, JoinEmpty) {
+  std::vector<SpdyStringPiece> empty;
+  SpdyStringPiece separator = ", ";
+  char buf[10] = "";
+  size_t written = Join(buf, empty, separator);
+  EXPECT_EQ(0u, written);
+}
+
+TEST(JoinTest, JoinOne) {
+  std::vector<SpdyStringPiece> v = {"one"};
+  SpdyStringPiece separator = ", ";
+  char buf[15];
+  size_t written = Join(buf, v, separator);
+  EXPECT_EQ(3u, written);
+  EXPECT_EQ("one", SpdyStringPiece(buf, written));
+}
+
+TEST(JoinTest, JoinMultiple) {
+  std::vector<SpdyStringPiece> v = {"one", "two", "three"};
+  SpdyStringPiece separator = ", ";
+  char buf[15];
+  size_t written = Join(buf, v, separator);
+  EXPECT_EQ(15u, written);
+  EXPECT_EQ("one, two, three", SpdyStringPiece(buf, written));
+}
+
+namespace {
+size_t SpdyHeaderBlockSize(const SpdyHeaderBlock& block) {
+  size_t size = 0;
+  for (const auto& pair : block) {
+    size += pair.first.size() + pair.second.size();
+  }
+  return size;
+}
+}  // namespace
+
+// Tests SpdyHeaderBlock SizeEstimate().
+TEST(SpdyHeaderBlockTest, TotalBytesUsed) {
+  SpdyHeaderBlock block;
+  const size_t value_size = 300;
+  block["foo"] = SpdyString(value_size, 'x');
+  EXPECT_EQ(block.TotalBytesUsed(), SpdyHeaderBlockSize(block));
+  block.insert(std::make_pair("key", SpdyString(value_size, 'x')));
+  EXPECT_EQ(block.TotalBytesUsed(), SpdyHeaderBlockSize(block));
+  block.AppendValueOrAddHeader("abc", SpdyString(value_size, 'x'));
+  EXPECT_EQ(block.TotalBytesUsed(), SpdyHeaderBlockSize(block));
+
+  // Replace value for existing key.
+  block["foo"] = SpdyString(value_size, 'x');
+  EXPECT_EQ(block.TotalBytesUsed(), SpdyHeaderBlockSize(block));
+  block.insert(std::make_pair("key", SpdyString(value_size, 'x')));
+  EXPECT_EQ(block.TotalBytesUsed(), SpdyHeaderBlockSize(block));
+  // Add value for existing key.
+  block.AppendValueOrAddHeader("abc", SpdyString(value_size, 'x'));
+  EXPECT_EQ(block.TotalBytesUsed(), SpdyHeaderBlockSize(block));
+
+  // Copies/clones SpdyHeaderBlock.
+  size_t block_size = block.TotalBytesUsed();
+  SpdyHeaderBlock block_copy = std::move(block);
+  EXPECT_EQ(block_size, block_copy.TotalBytesUsed());
+
+  // Erases key.
+  block_copy.erase("foo");
+  EXPECT_EQ(block_copy.TotalBytesUsed(), SpdyHeaderBlockSize(block_copy));
+  block_copy.erase("key");
+  EXPECT_EQ(block_copy.TotalBytesUsed(), SpdyHeaderBlockSize(block_copy));
+  block_copy.erase("abc");
+  EXPECT_EQ(block_copy.TotalBytesUsed(), SpdyHeaderBlockSize(block_copy));
+}
+
+}  // namespace test
+}  // namespace spdy
diff --git a/spdy/core/spdy_headers_handler_interface.h b/spdy/core/spdy_headers_handler_interface.h
new file mode 100644
index 0000000..ce6c1b6
--- /dev/null
+++ b/spdy/core/spdy_headers_handler_interface.h
@@ -0,0 +1,39 @@
+// Copyright 2015 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef QUICHE_SPDY_CORE_SPDY_HEADERS_HANDLER_INTERFACE_H_
+#define QUICHE_SPDY_CORE_SPDY_HEADERS_HANDLER_INTERFACE_H_
+
+#include <stddef.h>
+
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_export.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string_piece.h"
+
+namespace spdy {
+
+// This interface defines how an object that accepts header data should behave.
+// It is used by both SpdyHeadersBlockParser and HpackDecoder.
+class SPDY_EXPORT_PRIVATE SpdyHeadersHandlerInterface {
+ public:
+  virtual ~SpdyHeadersHandlerInterface() {}
+
+  // A callback method which notifies when the parser starts handling a new
+  // header block. Will only be called once per block, even if it extends into
+  // CONTINUATION frames.
+  virtual void OnHeaderBlockStart() = 0;
+
+  // A callback method which notifies on a header key value pair. Multiple
+  // values for a given key will be emitted as multiple calls to OnHeader.
+  virtual void OnHeader(SpdyStringPiece key, SpdyStringPiece value) = 0;
+
+  // A callback method which notifies when the parser finishes handling a
+  // header block (i.e. the containing frame has the END_HEADERS flag set).
+  // Also indicates the total number of bytes in this block.
+  virtual void OnHeaderBlockEnd(size_t uncompressed_header_bytes,
+                                size_t compressed_header_bytes) = 0;
+};
+
+}  // namespace spdy
+
+#endif  // QUICHE_SPDY_CORE_SPDY_HEADERS_HANDLER_INTERFACE_H_
diff --git a/spdy/core/spdy_no_op_visitor.cc b/spdy/core/spdy_no_op_visitor.cc
new file mode 100644
index 0000000..5dcc15c
--- /dev/null
+++ b/spdy/core/spdy_no_op_visitor.cc
@@ -0,0 +1,29 @@
+// Copyright (c) 2016 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "net/third_party/quiche/src/spdy/core/spdy_no_op_visitor.h"
+
+#include <type_traits>
+
+namespace spdy {
+namespace test {
+
+SpdyNoOpVisitor::SpdyNoOpVisitor() {
+  static_assert(std::is_abstract<SpdyNoOpVisitor>::value == false,
+                "Need to update SpdyNoOpVisitor.");
+}
+SpdyNoOpVisitor::~SpdyNoOpVisitor() = default;
+
+SpdyHeadersHandlerInterface* SpdyNoOpVisitor::OnHeaderFrameStart(
+    SpdyStreamId stream_id) {
+  return this;
+}
+
+bool SpdyNoOpVisitor::OnUnknownFrame(SpdyStreamId stream_id,
+                                     uint8_t frame_type) {
+  return true;
+}
+
+}  // namespace test
+}  // namespace spdy
diff --git a/spdy/core/spdy_no_op_visitor.h b/spdy/core/spdy_no_op_visitor.h
new file mode 100644
index 0000000..80e1535
--- /dev/null
+++ b/spdy/core/spdy_no_op_visitor.h
@@ -0,0 +1,89 @@
+// Copyright (c) 2016 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+// SpdyNoOpVisitor implements several of the visitor and handler interfaces
+// to make it easier to write tests that need to provide instances. Other
+// interfaces can be added as needed.
+
+#ifndef QUICHE_SPDY_CORE_SPDY_NO_OP_VISITOR_H_
+#define QUICHE_SPDY_CORE_SPDY_NO_OP_VISITOR_H_
+
+#include <cstdint>
+
+#include "net/third_party/quiche/src/spdy/core/http2_frame_decoder_adapter.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_protocol.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string_piece.h"
+
+namespace spdy {
+namespace test {
+
+class SpdyNoOpVisitor : public SpdyFramerVisitorInterface,
+                        public SpdyFramerDebugVisitorInterface,
+                        public SpdyHeadersHandlerInterface {
+ public:
+  SpdyNoOpVisitor();
+  ~SpdyNoOpVisitor() override;
+
+  // SpdyFramerVisitorInterface methods:
+  void OnError(http2::Http2DecoderAdapter::SpdyFramerError error) override {}
+  SpdyHeadersHandlerInterface* OnHeaderFrameStart(
+      SpdyStreamId stream_id) override;
+  void OnHeaderFrameEnd(SpdyStreamId stream_id) override {}
+  void OnDataFrameHeader(SpdyStreamId stream_id,
+                         size_t length,
+                         bool fin) override {}
+  void OnStreamFrameData(SpdyStreamId stream_id,
+                         const char* data,
+                         size_t len) override {}
+  void OnStreamEnd(SpdyStreamId stream_id) override {}
+  void OnStreamPadding(SpdyStreamId stream_id, size_t len) override {}
+  void OnRstStream(SpdyStreamId stream_id, SpdyErrorCode error_code) override {}
+  void OnSetting(SpdySettingsId id, uint32_t value) override {}
+  void OnPing(SpdyPingId unique_id, bool is_ack) override {}
+  void OnSettingsEnd() override {}
+  void OnSettingsAck() override {}
+  void OnGoAway(SpdyStreamId last_accepted_stream_id,
+                SpdyErrorCode error_code) override {}
+  void OnHeaders(SpdyStreamId stream_id,
+                 bool has_priority,
+                 int weight,
+                 SpdyStreamId parent_stream_id,
+                 bool exclusive,
+                 bool fin,
+                 bool end) override {}
+  void OnWindowUpdate(SpdyStreamId stream_id, int delta_window_size) override {}
+  void OnPushPromise(SpdyStreamId stream_id,
+                     SpdyStreamId promised_stream_id,
+                     bool end) override {}
+  void OnContinuation(SpdyStreamId stream_id, bool end) override {}
+  void OnAltSvc(SpdyStreamId stream_id,
+                SpdyStringPiece origin,
+                const SpdyAltSvcWireFormat::AlternativeServiceVector&
+                    altsvc_vector) override {}
+  void OnPriority(SpdyStreamId stream_id,
+                  SpdyStreamId parent_stream_id,
+                  int weight,
+                  bool exclusive) override {}
+  bool OnUnknownFrame(SpdyStreamId stream_id, uint8_t frame_type) override;
+
+  // SpdyFramerDebugVisitorInterface methods:
+  void OnSendCompressedFrame(SpdyStreamId stream_id,
+                             SpdyFrameType type,
+                             size_t payload_len,
+                             size_t frame_len) override {}
+  void OnReceiveCompressedFrame(SpdyStreamId stream_id,
+                                SpdyFrameType type,
+                                size_t frame_len) override {}
+
+  // SpdyHeadersHandlerInterface methods:
+  void OnHeaderBlockStart() override {}
+  void OnHeader(SpdyStringPiece key, SpdyStringPiece value) override {}
+  void OnHeaderBlockEnd(size_t /* uncompressed_header_bytes */,
+                        size_t /* compressed_header_bytes */) override {}
+};
+
+}  // namespace test
+}  // namespace spdy
+
+#endif  // QUICHE_SPDY_CORE_SPDY_NO_OP_VISITOR_H_
diff --git a/spdy/core/spdy_pinnable_buffer_piece.cc b/spdy/core/spdy_pinnable_buffer_piece.cc
new file mode 100644
index 0000000..8670962
--- /dev/null
+++ b/spdy/core/spdy_pinnable_buffer_piece.cc
@@ -0,0 +1,36 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "net/third_party/quiche/src/spdy/core/spdy_pinnable_buffer_piece.h"
+
+#include <new>
+
+namespace spdy {
+
+SpdyPinnableBufferPiece::SpdyPinnableBufferPiece()
+    : buffer_(nullptr), length_(0) {}
+
+SpdyPinnableBufferPiece::~SpdyPinnableBufferPiece() = default;
+
+void SpdyPinnableBufferPiece::Pin() {
+  if (!storage_ && buffer_ != nullptr && length_ != 0) {
+    storage_.reset(new char[length_]);
+    std::copy(buffer_, buffer_ + length_, storage_.get());
+    buffer_ = storage_.get();
+  }
+}
+
+void SpdyPinnableBufferPiece::Swap(SpdyPinnableBufferPiece* other) {
+  size_t length = length_;
+  length_ = other->length_;
+  other->length_ = length;
+
+  const char* buffer = buffer_;
+  buffer_ = other->buffer_;
+  other->buffer_ = buffer;
+
+  storage_.swap(other->storage_);
+}
+
+}  // namespace spdy
diff --git a/spdy/core/spdy_pinnable_buffer_piece.h b/spdy/core/spdy_pinnable_buffer_piece.h
new file mode 100644
index 0000000..3032ad7
--- /dev/null
+++ b/spdy/core/spdy_pinnable_buffer_piece.h
@@ -0,0 +1,53 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef QUICHE_SPDY_CORE_SPDY_PINNABLE_BUFFER_PIECE_H_
+#define QUICHE_SPDY_CORE_SPDY_PINNABLE_BUFFER_PIECE_H_
+
+#include <stddef.h>
+
+#include <memory>
+
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_export.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string_piece.h"
+
+namespace spdy {
+
+class SpdyPrefixedBufferReader;
+
+// Helper class of SpdyPrefixedBufferReader.
+// Represents a piece of consumed buffer which may (or may not) own its
+// underlying storage. Users may "pin" the buffer at a later time to ensure
+// a SpdyPinnableBufferPiece owns and retains storage of the buffer.
+struct SPDY_EXPORT_PRIVATE SpdyPinnableBufferPiece {
+ public:
+  SpdyPinnableBufferPiece();
+  ~SpdyPinnableBufferPiece();
+
+  const char* buffer() const { return buffer_; }
+
+  explicit operator SpdyStringPiece() const {
+    return SpdyStringPiece(buffer_, length_);
+  }
+
+  // Allocates and copies the buffer to internal storage.
+  void Pin();
+
+  bool IsPinned() const { return storage_ != nullptr; }
+
+  // Swaps buffers, including internal storage, with |other|.
+  void Swap(SpdyPinnableBufferPiece* other);
+
+ private:
+  friend class SpdyPrefixedBufferReader;
+
+  const char* buffer_;
+  size_t length_;
+  // Null iff |buffer_| isn't pinned.
+  std::unique_ptr<char[]> storage_;
+};
+
+}  // namespace spdy
+
+#endif  // QUICHE_SPDY_CORE_SPDY_PINNABLE_BUFFER_PIECE_H_
diff --git a/spdy/core/spdy_pinnable_buffer_piece_test.cc b/spdy/core/spdy_pinnable_buffer_piece_test.cc
new file mode 100644
index 0000000..d5a6c33
--- /dev/null
+++ b/spdy/core/spdy_pinnable_buffer_piece_test.cc
@@ -0,0 +1,80 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "net/third_party/quiche/src/spdy/core/spdy_pinnable_buffer_piece.h"
+
+#include "testing/gmock/include/gmock/gmock.h"
+#include "testing/gtest/include/gtest/gtest.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_prefixed_buffer_reader.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string.h"
+
+namespace spdy {
+
+namespace test {
+
+class SpdyPinnableBufferPieceTest : public ::testing::Test {
+ protected:
+  SpdyPrefixedBufferReader Build(const SpdyString& prefix,
+                                 const SpdyString& suffix) {
+    prefix_ = prefix;
+    suffix_ = suffix;
+    return SpdyPrefixedBufferReader(prefix_.data(), prefix_.length(),
+                                    suffix_.data(), suffix_.length());
+  }
+  SpdyString prefix_, suffix_;
+};
+
+TEST_F(SpdyPinnableBufferPieceTest, Pin) {
+  SpdyPrefixedBufferReader reader = Build("foobar", "");
+  SpdyPinnableBufferPiece piece;
+  EXPECT_TRUE(reader.ReadN(6, &piece));
+
+  // Piece points to underlying prefix storage.
+  EXPECT_EQ(SpdyStringPiece("foobar"), SpdyStringPiece(piece));
+  EXPECT_FALSE(piece.IsPinned());
+  EXPECT_EQ(prefix_.data(), piece.buffer());
+
+  piece.Pin();
+
+  // Piece now points to allocated storage.
+  EXPECT_EQ(SpdyStringPiece("foobar"), SpdyStringPiece(piece));
+  EXPECT_TRUE(piece.IsPinned());
+  EXPECT_NE(prefix_.data(), piece.buffer());
+
+  // Pinning again has no effect.
+  const char* buffer = piece.buffer();
+  piece.Pin();
+  EXPECT_EQ(buffer, piece.buffer());
+}
+
+TEST_F(SpdyPinnableBufferPieceTest, Swap) {
+  SpdyPrefixedBufferReader reader = Build("foobar", "");
+  SpdyPinnableBufferPiece piece1, piece2;
+  EXPECT_TRUE(reader.ReadN(4, &piece1));
+  EXPECT_TRUE(reader.ReadN(2, &piece2));
+
+  piece1.Pin();
+
+  EXPECT_EQ(SpdyStringPiece("foob"), SpdyStringPiece(piece1));
+  EXPECT_TRUE(piece1.IsPinned());
+  EXPECT_EQ(SpdyStringPiece("ar"), SpdyStringPiece(piece2));
+  EXPECT_FALSE(piece2.IsPinned());
+
+  piece1.Swap(&piece2);
+
+  EXPECT_EQ(SpdyStringPiece("ar"), SpdyStringPiece(piece1));
+  EXPECT_FALSE(piece1.IsPinned());
+  EXPECT_EQ(SpdyStringPiece("foob"), SpdyStringPiece(piece2));
+  EXPECT_TRUE(piece2.IsPinned());
+
+  SpdyPinnableBufferPiece empty;
+  piece2.Swap(&empty);
+
+  EXPECT_EQ(SpdyStringPiece(""), SpdyStringPiece(piece2));
+  EXPECT_FALSE(piece2.IsPinned());
+}
+
+}  // namespace test
+
+}  // namespace spdy
diff --git a/spdy/core/spdy_prefixed_buffer_reader.cc b/spdy/core/spdy_prefixed_buffer_reader.cc
new file mode 100644
index 0000000..9f1fa7f
--- /dev/null
+++ b/spdy/core/spdy_prefixed_buffer_reader.cc
@@ -0,0 +1,84 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "net/third_party/quiche/src/spdy/core/spdy_prefixed_buffer_reader.h"
+
+#include <new>
+
+#include "base/logging.h"
+
+namespace spdy {
+
+SpdyPrefixedBufferReader::SpdyPrefixedBufferReader(const char* prefix,
+                                                   size_t prefix_length,
+                                                   const char* suffix,
+                                                   size_t suffix_length)
+    : prefix_(prefix),
+      suffix_(suffix),
+      prefix_length_(prefix_length),
+      suffix_length_(suffix_length) {}
+
+size_t SpdyPrefixedBufferReader::Available() {
+  return prefix_length_ + suffix_length_;
+}
+
+bool SpdyPrefixedBufferReader::ReadN(size_t count, char* out) {
+  if (Available() < count) {
+    return false;
+  }
+
+  if (prefix_length_ >= count) {
+    // Read is fully satisfied by the prefix.
+    std::copy(prefix_, prefix_ + count, out);
+    prefix_ += count;
+    prefix_length_ -= count;
+    return true;
+  } else if (prefix_length_ != 0) {
+    // Read is partially satisfied by the prefix.
+    out = std::copy(prefix_, prefix_ + prefix_length_, out);
+    count -= prefix_length_;
+    prefix_length_ = 0;
+    // Fallthrough to suffix read.
+  }
+  DCHECK(suffix_length_ >= count);
+  // Read is satisfied by the suffix.
+  std::copy(suffix_, suffix_ + count, out);
+  suffix_ += count;
+  suffix_length_ -= count;
+  return true;
+}
+
+bool SpdyPrefixedBufferReader::ReadN(size_t count,
+                                     SpdyPinnableBufferPiece* out) {
+  if (Available() < count) {
+    return false;
+  }
+
+  out->storage_.reset();
+  out->length_ = count;
+
+  if (prefix_length_ >= count) {
+    // Read is fully satisfied by the prefix.
+    out->buffer_ = prefix_;
+    prefix_ += count;
+    prefix_length_ -= count;
+    return true;
+  } else if (prefix_length_ != 0) {
+    // Read is only partially satisfied by the prefix. We need to allocate
+    // contiguous storage as the read spans the prefix & suffix.
+    out->storage_.reset(new char[count]);
+    out->buffer_ = out->storage_.get();
+    ReadN(count, out->storage_.get());
+    return true;
+  } else {
+    DCHECK(suffix_length_ >= count);
+    // Read is fully satisfied by the suffix.
+    out->buffer_ = suffix_;
+    suffix_ += count;
+    suffix_length_ -= count;
+    return true;
+  }
+}
+
+}  // namespace spdy
diff --git a/spdy/core/spdy_prefixed_buffer_reader.h b/spdy/core/spdy_prefixed_buffer_reader.h
new file mode 100644
index 0000000..2905698
--- /dev/null
+++ b/spdy/core/spdy_prefixed_buffer_reader.h
@@ -0,0 +1,45 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef QUICHE_SPDY_CORE_SPDY_PREFIXED_BUFFER_READER_H_
+#define QUICHE_SPDY_CORE_SPDY_PREFIXED_BUFFER_READER_H_
+
+#include <stddef.h>
+
+#include "net/third_party/quiche/src/spdy/core/spdy_pinnable_buffer_piece.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_export.h"
+
+namespace spdy {
+
+// Reader class which simplifies reading contiguously from
+// from a disjoint buffer prefix & suffix.
+class SPDY_EXPORT_PRIVATE SpdyPrefixedBufferReader {
+ public:
+  SpdyPrefixedBufferReader(const char* prefix,
+                           size_t prefix_length,
+                           const char* suffix,
+                           size_t suffix_length);
+
+  // Returns number of bytes available to be read.
+  size_t Available();
+
+  // Reads |count| bytes, copying into |*out|. Returns true on success,
+  // false if not enough bytes were available.
+  bool ReadN(size_t count, char* out);
+
+  // Reads |count| bytes, returned in |*out|. Returns true on success,
+  // false if not enough bytes were available.
+  bool ReadN(size_t count, SpdyPinnableBufferPiece* out);
+
+ private:
+  const char* prefix_;
+  const char* suffix_;
+
+  size_t prefix_length_;
+  size_t suffix_length_;
+};
+
+}  // namespace spdy
+
+#endif  // QUICHE_SPDY_CORE_SPDY_PREFIXED_BUFFER_READER_H_
diff --git a/spdy/core/spdy_prefixed_buffer_reader_test.cc b/spdy/core/spdy_prefixed_buffer_reader_test.cc
new file mode 100644
index 0000000..1d052c7
--- /dev/null
+++ b/spdy/core/spdy_prefixed_buffer_reader_test.cc
@@ -0,0 +1,131 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "net/third_party/quiche/src/spdy/core/spdy_prefixed_buffer_reader.h"
+
+#include "testing/gmock/include/gmock/gmock.h"
+#include "testing/gtest/include/gtest/gtest.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string_piece.h"
+
+namespace spdy {
+
+namespace test {
+
+using testing::ElementsAreArray;
+
+class SpdyPrefixedBufferReaderTest : public ::testing::Test {
+ protected:
+  SpdyPrefixedBufferReader Build(const SpdyString& prefix,
+                                 const SpdyString& suffix) {
+    prefix_ = prefix;
+    suffix_ = suffix;
+    return SpdyPrefixedBufferReader(prefix_.data(), prefix_.length(),
+                                    suffix_.data(), suffix_.length());
+  }
+  SpdyString prefix_, suffix_;
+};
+
+TEST_F(SpdyPrefixedBufferReaderTest, ReadRawFromPrefix) {
+  SpdyPrefixedBufferReader reader = Build("foobar", "");
+  EXPECT_EQ(6u, reader.Available());
+
+  char buffer[] = "123456";
+  EXPECT_FALSE(reader.ReadN(10, buffer));  // Not enough buffer.
+  EXPECT_TRUE(reader.ReadN(6, buffer));
+  EXPECT_THAT(buffer, ElementsAreArray("foobar"));
+  EXPECT_EQ(0u, reader.Available());
+}
+
+TEST_F(SpdyPrefixedBufferReaderTest, ReadPieceFromPrefix) {
+  SpdyPrefixedBufferReader reader = Build("foobar", "");
+  EXPECT_EQ(6u, reader.Available());
+
+  SpdyPinnableBufferPiece piece;
+  EXPECT_FALSE(reader.ReadN(10, &piece));  // Not enough buffer.
+  EXPECT_TRUE(reader.ReadN(6, &piece));
+  EXPECT_FALSE(piece.IsPinned());
+  EXPECT_EQ(SpdyStringPiece("foobar"), SpdyStringPiece(piece));
+  EXPECT_EQ(0u, reader.Available());
+}
+
+TEST_F(SpdyPrefixedBufferReaderTest, ReadRawFromSuffix) {
+  SpdyPrefixedBufferReader reader = Build("", "foobar");
+  EXPECT_EQ(6u, reader.Available());
+
+  char buffer[] = "123456";
+  EXPECT_FALSE(reader.ReadN(10, buffer));  // Not enough buffer.
+  EXPECT_TRUE(reader.ReadN(6, buffer));
+  EXPECT_THAT(buffer, ElementsAreArray("foobar"));
+  EXPECT_EQ(0u, reader.Available());
+}
+
+TEST_F(SpdyPrefixedBufferReaderTest, ReadPieceFromSuffix) {
+  SpdyPrefixedBufferReader reader = Build("", "foobar");
+  EXPECT_EQ(6u, reader.Available());
+
+  SpdyPinnableBufferPiece piece;
+  EXPECT_FALSE(reader.ReadN(10, &piece));  // Not enough buffer.
+  EXPECT_TRUE(reader.ReadN(6, &piece));
+  EXPECT_FALSE(piece.IsPinned());
+  EXPECT_EQ(SpdyStringPiece("foobar"), SpdyStringPiece(piece));
+  EXPECT_EQ(0u, reader.Available());
+}
+
+TEST_F(SpdyPrefixedBufferReaderTest, ReadRawSpanning) {
+  SpdyPrefixedBufferReader reader = Build("foob", "ar");
+  EXPECT_EQ(6u, reader.Available());
+
+  char buffer[] = "123456";
+  EXPECT_FALSE(reader.ReadN(10, buffer));  // Not enough buffer.
+  EXPECT_TRUE(reader.ReadN(6, buffer));
+  EXPECT_THAT(buffer, ElementsAreArray("foobar"));
+  EXPECT_EQ(0u, reader.Available());
+}
+
+TEST_F(SpdyPrefixedBufferReaderTest, ReadPieceSpanning) {
+  SpdyPrefixedBufferReader reader = Build("foob", "ar");
+  EXPECT_EQ(6u, reader.Available());
+
+  SpdyPinnableBufferPiece piece;
+  EXPECT_FALSE(reader.ReadN(10, &piece));  // Not enough buffer.
+  EXPECT_TRUE(reader.ReadN(6, &piece));
+  EXPECT_TRUE(piece.IsPinned());
+  EXPECT_EQ(SpdyStringPiece("foobar"), SpdyStringPiece(piece));
+  EXPECT_EQ(0u, reader.Available());
+}
+
+TEST_F(SpdyPrefixedBufferReaderTest, ReadMixed) {
+  SpdyPrefixedBufferReader reader = Build("abcdef", "hijkl");
+  EXPECT_EQ(11u, reader.Available());
+
+  char buffer[] = "1234";
+  SpdyPinnableBufferPiece piece;
+
+  EXPECT_TRUE(reader.ReadN(3, buffer));
+  EXPECT_THAT(buffer, ElementsAreArray("abc4"));
+  EXPECT_EQ(8u, reader.Available());
+
+  EXPECT_TRUE(reader.ReadN(2, buffer));
+  EXPECT_THAT(buffer, ElementsAreArray("dec4"));
+  EXPECT_EQ(6u, reader.Available());
+
+  EXPECT_TRUE(reader.ReadN(3, &piece));
+  EXPECT_EQ(SpdyStringPiece("fhi"), SpdyStringPiece(piece));
+  EXPECT_TRUE(piece.IsPinned());
+  EXPECT_EQ(3u, reader.Available());
+
+  EXPECT_TRUE(reader.ReadN(2, &piece));
+  EXPECT_EQ(SpdyStringPiece("jk"), SpdyStringPiece(piece));
+  EXPECT_FALSE(piece.IsPinned());
+  EXPECT_EQ(1u, reader.Available());
+
+  EXPECT_TRUE(reader.ReadN(1, buffer));
+  EXPECT_THAT(buffer, ElementsAreArray("lec4"));
+  EXPECT_EQ(0u, reader.Available());
+}
+
+}  // namespace test
+
+}  // namespace spdy
diff --git a/spdy/core/spdy_protocol.cc b/spdy/core/spdy_protocol.cc
new file mode 100644
index 0000000..f51dc6e
--- /dev/null
+++ b/spdy/core/spdy_protocol.cc
@@ -0,0 +1,571 @@
+// Copyright (c) 2012 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "net/third_party/quiche/src/spdy/core/spdy_protocol.h"
+
+#include <ostream>
+
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_bug_tracker.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_ptr_util.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string_utils.h"
+
+namespace spdy {
+
+const char* const kHttp2ConnectionHeaderPrefix =
+    "PRI * HTTP/2.0\r\n\r\nSM\r\n\r\n";
+
+std::ostream& operator<<(std::ostream& out, SpdyKnownSettingsId id) {
+  return out << static_cast<SpdySettingsId>(id);
+}
+
+std::ostream& operator<<(std::ostream& out, SpdyFrameType frame_type) {
+  return out << SerializeFrameType(frame_type);
+}
+
+SpdyPriority ClampSpdy3Priority(SpdyPriority priority) {
+  if (priority < kV3HighestPriority) {
+    SPDY_BUG << "Invalid priority: " << static_cast<int>(priority);
+    return kV3HighestPriority;
+  }
+  if (priority > kV3LowestPriority) {
+    SPDY_BUG << "Invalid priority: " << static_cast<int>(priority);
+    return kV3LowestPriority;
+  }
+  return priority;
+}
+
+int ClampHttp2Weight(int weight) {
+  if (weight < kHttp2MinStreamWeight) {
+    SPDY_BUG << "Invalid weight: " << weight;
+    return kHttp2MinStreamWeight;
+  }
+  if (weight > kHttp2MaxStreamWeight) {
+    SPDY_BUG << "Invalid weight: " << weight;
+    return kHttp2MaxStreamWeight;
+  }
+  return weight;
+}
+
+int Spdy3PriorityToHttp2Weight(SpdyPriority priority) {
+  priority = ClampSpdy3Priority(priority);
+  const float kSteps = 255.9f / 7.f;
+  return static_cast<int>(kSteps * (7.f - priority)) + 1;
+}
+
+SpdyPriority Http2WeightToSpdy3Priority(int weight) {
+  weight = ClampHttp2Weight(weight);
+  const float kSteps = 255.9f / 7.f;
+  return static_cast<SpdyPriority>(7.f - (weight - 1) / kSteps);
+}
+
+bool IsDefinedFrameType(uint8_t frame_type_field) {
+  return frame_type_field <= SerializeFrameType(SpdyFrameType::MAX_FRAME_TYPE);
+}
+
+SpdyFrameType ParseFrameType(uint8_t frame_type_field) {
+  SPDY_BUG_IF(!IsDefinedFrameType(frame_type_field))
+      << "Frame type not defined: " << static_cast<int>(frame_type_field);
+  return static_cast<SpdyFrameType>(frame_type_field);
+}
+
+uint8_t SerializeFrameType(SpdyFrameType frame_type) {
+  return static_cast<uint8_t>(frame_type);
+}
+
+bool IsValidHTTP2FrameStreamId(SpdyStreamId current_frame_stream_id,
+                               SpdyFrameType frame_type_field) {
+  if (current_frame_stream_id == 0) {
+    switch (frame_type_field) {
+      case SpdyFrameType::DATA:
+      case SpdyFrameType::HEADERS:
+      case SpdyFrameType::PRIORITY:
+      case SpdyFrameType::RST_STREAM:
+      case SpdyFrameType::CONTINUATION:
+      case SpdyFrameType::PUSH_PROMISE:
+        // These frame types must specify a stream
+        return false;
+      default:
+        return true;
+    }
+  } else {
+    switch (frame_type_field) {
+      case SpdyFrameType::GOAWAY:
+      case SpdyFrameType::SETTINGS:
+      case SpdyFrameType::PING:
+        // These frame types must not specify a stream
+        return false;
+      default:
+        return true;
+    }
+  }
+}
+
+const char* FrameTypeToString(SpdyFrameType frame_type) {
+  switch (frame_type) {
+    case SpdyFrameType::DATA:
+      return "DATA";
+    case SpdyFrameType::RST_STREAM:
+      return "RST_STREAM";
+    case SpdyFrameType::SETTINGS:
+      return "SETTINGS";
+    case SpdyFrameType::PING:
+      return "PING";
+    case SpdyFrameType::GOAWAY:
+      return "GOAWAY";
+    case SpdyFrameType::HEADERS:
+      return "HEADERS";
+    case SpdyFrameType::WINDOW_UPDATE:
+      return "WINDOW_UPDATE";
+    case SpdyFrameType::PUSH_PROMISE:
+      return "PUSH_PROMISE";
+    case SpdyFrameType::CONTINUATION:
+      return "CONTINUATION";
+    case SpdyFrameType::PRIORITY:
+      return "PRIORITY";
+    case SpdyFrameType::ALTSVC:
+      return "ALTSVC";
+    case SpdyFrameType::EXTENSION:
+      return "EXTENSION (unspecified)";
+  }
+  return "UNKNOWN_FRAME_TYPE";
+}
+
+bool ParseSettingsId(SpdySettingsId wire_setting_id,
+                     SpdyKnownSettingsId* setting_id) {
+  if (wire_setting_id != SETTINGS_EXPERIMENT_SCHEDULER &&
+      (wire_setting_id < SETTINGS_MIN || wire_setting_id > SETTINGS_MAX)) {
+    return false;
+  }
+
+  *setting_id = static_cast<SpdyKnownSettingsId>(wire_setting_id);
+  // This switch ensures that the casted value is valid. The default case is
+  // explicitly omitted to have compile-time guarantees that new additions to
+  // |SpdyKnownSettingsId| must also be handled here.
+  switch (*setting_id) {
+    case SETTINGS_HEADER_TABLE_SIZE:
+    case SETTINGS_ENABLE_PUSH:
+    case SETTINGS_MAX_CONCURRENT_STREAMS:
+    case SETTINGS_INITIAL_WINDOW_SIZE:
+    case SETTINGS_MAX_FRAME_SIZE:
+    case SETTINGS_MAX_HEADER_LIST_SIZE:
+    case SETTINGS_ENABLE_CONNECT_PROTOCOL:
+    case SETTINGS_EXPERIMENT_SCHEDULER:
+      // FALLTHROUGH_INTENDED
+      return true;
+  }
+  return false;
+}
+
+SpdyString SettingsIdToString(SpdySettingsId id) {
+  SpdyKnownSettingsId known_id;
+  if (!ParseSettingsId(id, &known_id)) {
+    return SpdyStrCat("SETTINGS_UNKNOWN_",
+                      SpdyHexEncodeUInt32AndTrim(uint32_t{id}));
+  }
+
+  switch (known_id) {
+    case SETTINGS_HEADER_TABLE_SIZE:
+      return "SETTINGS_HEADER_TABLE_SIZE";
+    case SETTINGS_ENABLE_PUSH:
+      return "SETTINGS_ENABLE_PUSH";
+    case SETTINGS_MAX_CONCURRENT_STREAMS:
+      return "SETTINGS_MAX_CONCURRENT_STREAMS";
+    case SETTINGS_INITIAL_WINDOW_SIZE:
+      return "SETTINGS_INITIAL_WINDOW_SIZE";
+    case SETTINGS_MAX_FRAME_SIZE:
+      return "SETTINGS_MAX_FRAME_SIZE";
+    case SETTINGS_MAX_HEADER_LIST_SIZE:
+      return "SETTINGS_MAX_HEADER_LIST_SIZE";
+    case SETTINGS_ENABLE_CONNECT_PROTOCOL:
+      return "SETTINGS_ENABLE_CONNECT_PROTOCOL";
+    case SETTINGS_EXPERIMENT_SCHEDULER:
+      return "SETTINGS_EXPERIMENT_SCHEDULER";
+  }
+
+  return SpdyStrCat("SETTINGS_UNKNOWN_",
+                    SpdyHexEncodeUInt32AndTrim(uint32_t{id}));
+}
+
+SpdyErrorCode ParseErrorCode(uint32_t wire_error_code) {
+  if (wire_error_code > ERROR_CODE_MAX) {
+    return ERROR_CODE_INTERNAL_ERROR;
+  }
+
+  return static_cast<SpdyErrorCode>(wire_error_code);
+}
+
+const char* ErrorCodeToString(SpdyErrorCode error_code) {
+  switch (error_code) {
+    case ERROR_CODE_NO_ERROR:
+      return "NO_ERROR";
+    case ERROR_CODE_PROTOCOL_ERROR:
+      return "PROTOCOL_ERROR";
+    case ERROR_CODE_INTERNAL_ERROR:
+      return "INTERNAL_ERROR";
+    case ERROR_CODE_FLOW_CONTROL_ERROR:
+      return "FLOW_CONTROL_ERROR";
+    case ERROR_CODE_SETTINGS_TIMEOUT:
+      return "SETTINGS_TIMEOUT";
+    case ERROR_CODE_STREAM_CLOSED:
+      return "STREAM_CLOSED";
+    case ERROR_CODE_FRAME_SIZE_ERROR:
+      return "FRAME_SIZE_ERROR";
+    case ERROR_CODE_REFUSED_STREAM:
+      return "REFUSED_STREAM";
+    case ERROR_CODE_CANCEL:
+      return "CANCEL";
+    case ERROR_CODE_COMPRESSION_ERROR:
+      return "COMPRESSION_ERROR";
+    case ERROR_CODE_CONNECT_ERROR:
+      return "CONNECT_ERROR";
+    case ERROR_CODE_ENHANCE_YOUR_CALM:
+      return "ENHANCE_YOUR_CALM";
+    case ERROR_CODE_INADEQUATE_SECURITY:
+      return "INADEQUATE_SECURITY";
+    case ERROR_CODE_HTTP_1_1_REQUIRED:
+      return "HTTP_1_1_REQUIRED";
+  }
+  return "UNKNOWN_ERROR_CODE";
+}
+
+size_t GetNumberRequiredContinuationFrames(size_t size) {
+  DCHECK_GT(size, kHttp2MaxControlFrameSendSize);
+  size_t overflow = size - kHttp2MaxControlFrameSendSize;
+  int payload_size =
+      kHttp2MaxControlFrameSendSize - kContinuationFrameMinimumSize;
+  // This is ceiling(overflow/payload_size) using integer arithmetics.
+  return (overflow - 1) / payload_size + 1;
+}
+
+const char* const kHttp2Npn = "h2";
+
+const char* const kHttp2AuthorityHeader = ":authority";
+const char* const kHttp2MethodHeader = ":method";
+const char* const kHttp2PathHeader = ":path";
+const char* const kHttp2SchemeHeader = ":scheme";
+const char* const kHttp2ProtocolHeader = ":protocol";
+
+const char* const kHttp2StatusHeader = ":status";
+
+bool SpdyFrameIR::fin() const {
+  return false;
+}
+
+int SpdyFrameIR::flow_control_window_consumed() const {
+  return 0;
+}
+
+bool SpdyFrameWithFinIR::fin() const {
+  return fin_;
+}
+
+SpdyFrameWithHeaderBlockIR::SpdyFrameWithHeaderBlockIR(
+    SpdyStreamId stream_id,
+    SpdyHeaderBlock header_block)
+    : SpdyFrameWithFinIR(stream_id), header_block_(std::move(header_block)) {}
+
+SpdyFrameWithHeaderBlockIR::~SpdyFrameWithHeaderBlockIR() = default;
+
+SpdyDataIR::SpdyDataIR(SpdyStreamId stream_id, SpdyStringPiece data)
+    : SpdyFrameWithFinIR(stream_id),
+      data_(nullptr),
+      data_len_(0),
+      padded_(false),
+      padding_payload_len_(0) {
+  SetDataDeep(data);
+}
+
+SpdyDataIR::SpdyDataIR(SpdyStreamId stream_id, const char* data)
+    : SpdyDataIR(stream_id, SpdyStringPiece(data)) {}
+
+SpdyDataIR::SpdyDataIR(SpdyStreamId stream_id, SpdyString data)
+    : SpdyFrameWithFinIR(stream_id),
+      data_store_(SpdyMakeUnique<SpdyString>(std::move(data))),
+      data_(data_store_->data()),
+      data_len_(data_store_->size()),
+      padded_(false),
+      padding_payload_len_(0) {}
+
+SpdyDataIR::SpdyDataIR(SpdyStreamId stream_id)
+    : SpdyFrameWithFinIR(stream_id),
+      data_(nullptr),
+      data_len_(0),
+      padded_(false),
+      padding_payload_len_(0) {}
+
+SpdyDataIR::~SpdyDataIR() = default;
+
+void SpdyDataIR::Visit(SpdyFrameVisitor* visitor) const {
+  return visitor->VisitData(*this);
+}
+
+SpdyFrameType SpdyDataIR::frame_type() const {
+  return SpdyFrameType::DATA;
+}
+
+int SpdyDataIR::flow_control_window_consumed() const {
+  return padded_ ? 1 + padding_payload_len_ + data_len_ : data_len_;
+}
+
+size_t SpdyDataIR::size() const {
+  return kFrameHeaderSize +
+         (padded() ? 1 + padding_payload_len() + data_len() : data_len());
+}
+
+SpdyRstStreamIR::SpdyRstStreamIR(SpdyStreamId stream_id,
+                                 SpdyErrorCode error_code)
+    : SpdyFrameIR(stream_id) {
+  set_error_code(error_code);
+}
+
+SpdyRstStreamIR::~SpdyRstStreamIR() = default;
+
+void SpdyRstStreamIR::Visit(SpdyFrameVisitor* visitor) const {
+  return visitor->VisitRstStream(*this);
+}
+
+SpdyFrameType SpdyRstStreamIR::frame_type() const {
+  return SpdyFrameType::RST_STREAM;
+}
+
+size_t SpdyRstStreamIR::size() const {
+  return kRstStreamFrameSize;
+}
+
+SpdySettingsIR::SpdySettingsIR() : is_ack_(false) {}
+
+SpdySettingsIR::~SpdySettingsIR() = default;
+
+void SpdySettingsIR::Visit(SpdyFrameVisitor* visitor) const {
+  return visitor->VisitSettings(*this);
+}
+
+SpdyFrameType SpdySettingsIR::frame_type() const {
+  return SpdyFrameType::SETTINGS;
+}
+
+size_t SpdySettingsIR::size() const {
+  return kFrameHeaderSize + values_.size() * kSettingsOneSettingSize;
+}
+
+void SpdyPingIR::Visit(SpdyFrameVisitor* visitor) const {
+  return visitor->VisitPing(*this);
+}
+
+SpdyFrameType SpdyPingIR::frame_type() const {
+  return SpdyFrameType::PING;
+}
+
+size_t SpdyPingIR::size() const {
+  return kPingFrameSize;
+}
+
+SpdyGoAwayIR::SpdyGoAwayIR(SpdyStreamId last_good_stream_id,
+                           SpdyErrorCode error_code,
+                           SpdyStringPiece description)
+    : description_(description) {
+  set_last_good_stream_id(last_good_stream_id);
+  set_error_code(error_code);
+}
+
+SpdyGoAwayIR::SpdyGoAwayIR(SpdyStreamId last_good_stream_id,
+                           SpdyErrorCode error_code,
+                           const char* description)
+    : SpdyGoAwayIR(last_good_stream_id,
+                   error_code,
+                   SpdyStringPiece(description)) {}
+
+SpdyGoAwayIR::SpdyGoAwayIR(SpdyStreamId last_good_stream_id,
+                           SpdyErrorCode error_code,
+                           SpdyString description)
+    : description_store_(std::move(description)),
+      description_(description_store_) {
+  set_last_good_stream_id(last_good_stream_id);
+  set_error_code(error_code);
+}
+
+SpdyGoAwayIR::~SpdyGoAwayIR() = default;
+
+void SpdyGoAwayIR::Visit(SpdyFrameVisitor* visitor) const {
+  return visitor->VisitGoAway(*this);
+}
+
+SpdyFrameType SpdyGoAwayIR::frame_type() const {
+  return SpdyFrameType::GOAWAY;
+}
+
+size_t SpdyGoAwayIR::size() const {
+  return kGoawayFrameMinimumSize + description_.size();
+}
+
+SpdyContinuationIR::SpdyContinuationIR(SpdyStreamId stream_id)
+    : SpdyFrameIR(stream_id), end_headers_(false) {
+  encoding_ = SpdyMakeUnique<SpdyString>();
+}
+
+SpdyContinuationIR::~SpdyContinuationIR() = default;
+
+void SpdyContinuationIR::Visit(SpdyFrameVisitor* visitor) const {
+  return visitor->VisitContinuation(*this);
+}
+
+SpdyFrameType SpdyContinuationIR::frame_type() const {
+  return SpdyFrameType::CONTINUATION;
+}
+
+size_t SpdyContinuationIR::size() const {
+  // We don't need to get the size of CONTINUATION frame directly. It is
+  // calculated in HEADERS or PUSH_PROMISE frame.
+  DLOG(WARNING) << "Shouldn't not call size() for CONTINUATION frame.";
+  return 0;
+}
+
+void SpdyHeadersIR::Visit(SpdyFrameVisitor* visitor) const {
+  return visitor->VisitHeaders(*this);
+}
+
+SpdyFrameType SpdyHeadersIR::frame_type() const {
+  return SpdyFrameType::HEADERS;
+}
+
+size_t SpdyHeadersIR::size() const {
+  size_t size = kHeadersFrameMinimumSize;
+
+  if (padded_) {
+    // Padding field length.
+    size += 1;
+    size += padding_payload_len_;
+  }
+
+  if (has_priority_) {
+    size += 5;
+  }
+
+  // Assume no hpack encoding is applied.
+  size += header_block().TotalBytesUsed() +
+          header_block().size() * kPerHeaderHpackOverhead;
+  if (size > kHttp2MaxControlFrameSendSize) {
+    size += GetNumberRequiredContinuationFrames(size) *
+            kContinuationFrameMinimumSize;
+  }
+  return size;
+}
+
+void SpdyWindowUpdateIR::Visit(SpdyFrameVisitor* visitor) const {
+  return visitor->VisitWindowUpdate(*this);
+}
+
+SpdyFrameType SpdyWindowUpdateIR::frame_type() const {
+  return SpdyFrameType::WINDOW_UPDATE;
+}
+
+size_t SpdyWindowUpdateIR::size() const {
+  return kWindowUpdateFrameSize;
+}
+
+void SpdyPushPromiseIR::Visit(SpdyFrameVisitor* visitor) const {
+  return visitor->VisitPushPromise(*this);
+}
+
+SpdyFrameType SpdyPushPromiseIR::frame_type() const {
+  return SpdyFrameType::PUSH_PROMISE;
+}
+
+size_t SpdyPushPromiseIR::size() const {
+  size_t size = kPushPromiseFrameMinimumSize;
+
+  if (padded_) {
+    // Padding length field.
+    size += 1;
+    size += padding_payload_len_;
+  }
+
+  size += header_block().TotalBytesUsed();
+  if (size > kHttp2MaxControlFrameSendSize) {
+    size += GetNumberRequiredContinuationFrames(size) *
+            kContinuationFrameMinimumSize;
+  }
+  return size;
+}
+
+SpdyAltSvcIR::SpdyAltSvcIR(SpdyStreamId stream_id) : SpdyFrameIR(stream_id) {}
+
+SpdyAltSvcIR::~SpdyAltSvcIR() = default;
+
+void SpdyAltSvcIR::Visit(SpdyFrameVisitor* visitor) const {
+  return visitor->VisitAltSvc(*this);
+}
+
+SpdyFrameType SpdyAltSvcIR::frame_type() const {
+  return SpdyFrameType::ALTSVC;
+}
+
+size_t SpdyAltSvcIR::size() const {
+  size_t size = kGetAltSvcFrameMinimumSize;
+  size += origin_.length();
+  // TODO(yasong): estimates the size without serializing the vector.
+  SpdyString str =
+      SpdyAltSvcWireFormat::SerializeHeaderFieldValue(altsvc_vector_);
+  size += str.size();
+  return size;
+}
+
+void SpdyPriorityIR::Visit(SpdyFrameVisitor* visitor) const {
+  return visitor->VisitPriority(*this);
+}
+
+SpdyFrameType SpdyPriorityIR::frame_type() const {
+  return SpdyFrameType::PRIORITY;
+}
+
+size_t SpdyPriorityIR::size() const {
+  return kPriorityFrameSize;
+}
+
+void SpdyUnknownIR::Visit(SpdyFrameVisitor* visitor) const {
+  return visitor->VisitUnknown(*this);
+}
+
+SpdyFrameType SpdyUnknownIR::frame_type() const {
+  return static_cast<SpdyFrameType>(type());
+}
+
+size_t SpdyUnknownIR::size() const {
+  return kFrameHeaderSize + payload_.size();
+}
+
+int SpdyUnknownIR::flow_control_window_consumed() const {
+  if (frame_type() == SpdyFrameType::DATA) {
+    return payload_.size();
+  } else {
+    return 0;
+  }
+}
+
+// Wire size of pad length field.
+const size_t kPadLengthFieldSize = 1;
+
+size_t GetHeaderFrameSizeSansBlock(const SpdyHeadersIR& header_ir) {
+  size_t min_size = kFrameHeaderSize;
+  if (header_ir.padded()) {
+    min_size += kPadLengthFieldSize;
+    min_size += header_ir.padding_payload_len();
+  }
+  if (header_ir.has_priority()) {
+    min_size += 5;
+  }
+  return min_size;
+}
+
+size_t GetPushPromiseFrameSizeSansBlock(
+    const SpdyPushPromiseIR& push_promise_ir) {
+  size_t min_size = kPushPromiseFrameMinimumSize;
+  if (push_promise_ir.padded()) {
+    min_size += kPadLengthFieldSize;
+    min_size += push_promise_ir.padding_payload_len();
+  }
+  return min_size;
+}
+
+}  // namespace spdy
diff --git a/spdy/core/spdy_protocol.h b/spdy/core/spdy_protocol.h
new file mode 100644
index 0000000..d300d10
--- /dev/null
+++ b/spdy/core/spdy_protocol.h
@@ -0,0 +1,1066 @@
+// Copyright (c) 2012 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+// This file contains some protocol structures for use with SPDY 3 and HTTP 2
+// The SPDY 3 spec can be found at:
+// http://dev.chromium.org/spdy/spdy-protocol/spdy-protocol-draft3
+
+#ifndef QUICHE_SPDY_CORE_SPDY_PROTOCOL_H_
+#define QUICHE_SPDY_CORE_SPDY_PROTOCOL_H_
+
+#include <cstddef>
+#include <cstdint>
+#include <iosfwd>
+#include <limits>
+#include <map>
+#include <memory>
+#include <new>
+#include <utility>
+
+#include "base/logging.h"
+#include "base/macros.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_alt_svc_wire_format.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_bitmasks.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_header_block.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_bug_tracker.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_export.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_ptr_util.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string_piece.h"
+
+namespace spdy {
+
+// A stream ID is a 31-bit entity.
+using SpdyStreamId = uint32_t;
+
+// A SETTINGS ID is a 16-bit entity.
+using SpdySettingsId = uint16_t;
+
+// Specifies the stream ID used to denote the current session (for
+// flow control).
+const SpdyStreamId kSessionFlowControlStreamId = 0;
+
+// 0 is not a valid stream ID for any other purpose than flow control.
+const SpdyStreamId kInvalidStreamId = 0;
+
+// Max stream id.
+const SpdyStreamId kMaxStreamId = 0x7fffffff;
+
+// The maximum possible frame payload size allowed by the spec.
+const uint32_t kSpdyMaxFrameSizeLimit = (1 << 24) - 1;
+
+// The initial value for the maximum frame payload size as per the spec. This is
+// the maximum control frame size we accept.
+const uint32_t kHttp2DefaultFramePayloadLimit = 1 << 14;
+
+// The maximum size of the control frames that we send, including the size of
+// the header. This limit is arbitrary. We can enforce it here or at the
+// application layer. We chose the framing layer, but this can be changed (or
+// removed) if necessary later down the line.
+const size_t kHttp2MaxControlFrameSendSize = kHttp2DefaultFramePayloadLimit - 1;
+
+// Number of octets in the frame header.
+const size_t kFrameHeaderSize = 9;
+
+// The initial value for the maximum frame payload size as per the spec. This is
+// the maximum control frame size we accept.
+const uint32_t kHttp2DefaultFrameSizeLimit =
+    kHttp2DefaultFramePayloadLimit + kFrameHeaderSize;
+
+// The initial value for the maximum size of the header list, "unlimited" (max
+// unsigned 32-bit int) as per the spec.
+const uint32_t kSpdyInitialHeaderListSizeLimit = 0xFFFFFFFF;
+
+// Maximum window size for a Spdy stream or session.
+const int32_t kSpdyMaximumWindowSize = 0x7FFFFFFF;  // Max signed 32bit int
+
+// Maximum padding size in octets for one DATA or HEADERS or PUSH_PROMISE frame.
+const int32_t kPaddingSizePerFrame = 256;
+
+// The HTTP/2 connection preface, which must be the first bytes sent by the
+// client upon starting an HTTP/2 connection, and which must be followed by a
+// SETTINGS frame.  Note that even though |kHttp2ConnectionHeaderPrefix| is
+// defined as a string literal with a null terminator, the actual connection
+// preface is only the first |kHttp2ConnectionHeaderPrefixSize| bytes, which
+// excludes the null terminator.
+SPDY_EXPORT_PRIVATE extern const char* const kHttp2ConnectionHeaderPrefix;
+const int kHttp2ConnectionHeaderPrefixSize = 24;
+
+// Wire values for HTTP2 frame types.
+enum class SpdyFrameType : uint8_t {
+  DATA = 0x00,
+  HEADERS = 0x01,
+  PRIORITY = 0x02,
+  RST_STREAM = 0x03,
+  SETTINGS = 0x04,
+  PUSH_PROMISE = 0x05,
+  PING = 0x06,
+  GOAWAY = 0x07,
+  WINDOW_UPDATE = 0x08,
+  CONTINUATION = 0x09,
+  // ALTSVC is a public extension.
+  ALTSVC = 0x0a,
+  MAX_FRAME_TYPE = ALTSVC,
+  // The specific value of EXTENSION is meaningless; it is a placeholder used
+  // within SpdyFramer's state machine when handling unknown frames via an
+  // extension API.
+  // TODO(birenroy): Remove the fake EXTENSION value from the SpdyFrameType
+  // enum.
+  EXTENSION = 0xff
+};
+
+// Flags on data packets.
+enum SpdyDataFlags {
+  DATA_FLAG_NONE = 0x00,
+  DATA_FLAG_FIN = 0x01,
+  DATA_FLAG_PADDED = 0x08,
+};
+
+// Flags on control packets
+enum SpdyControlFlags {
+  CONTROL_FLAG_NONE = 0x00,
+  CONTROL_FLAG_FIN = 0x01,
+};
+
+enum SpdyPingFlags {
+  PING_FLAG_ACK = 0x01,
+};
+
+// Used by HEADERS, PUSH_PROMISE, and CONTINUATION.
+enum SpdyHeadersFlags {
+  HEADERS_FLAG_END_HEADERS = 0x04,
+  HEADERS_FLAG_PADDED = 0x08,
+  HEADERS_FLAG_PRIORITY = 0x20,
+};
+
+enum SpdyPushPromiseFlags {
+  PUSH_PROMISE_FLAG_END_PUSH_PROMISE = 0x04,
+  PUSH_PROMISE_FLAG_PADDED = 0x08,
+};
+
+enum Http2SettingsControlFlags {
+  SETTINGS_FLAG_ACK = 0x01,
+};
+
+// Wire values of HTTP/2 setting identifiers.
+enum SpdyKnownSettingsId : SpdySettingsId {
+  // HPACK header table maximum size.
+  SETTINGS_HEADER_TABLE_SIZE = 0x1,
+  SETTINGS_MIN = SETTINGS_HEADER_TABLE_SIZE,
+  // Whether or not server push (PUSH_PROMISE) is enabled.
+  SETTINGS_ENABLE_PUSH = 0x2,
+  // The maximum number of simultaneous live streams in each direction.
+  SETTINGS_MAX_CONCURRENT_STREAMS = 0x3,
+  // Initial window size in bytes
+  SETTINGS_INITIAL_WINDOW_SIZE = 0x4,
+  // The size of the largest frame payload that a receiver is willing to accept.
+  SETTINGS_MAX_FRAME_SIZE = 0x5,
+  // The maximum size of header list that the sender is prepared to accept.
+  SETTINGS_MAX_HEADER_LIST_SIZE = 0x6,
+  // Enable Websockets over HTTP/2, see
+  // https://tools.ietf.org/html/draft-ietf-httpbis-h2-websockets-00.
+  SETTINGS_ENABLE_CONNECT_PROTOCOL = 0x8,
+  SETTINGS_MAX = SETTINGS_ENABLE_CONNECT_PROTOCOL,
+  // Experimental setting used to configure an alternative write scheduler.
+  SETTINGS_EXPERIMENT_SCHEDULER = 0xFF45,
+};
+
+// This explicit operator is needed, otherwise compiler finds
+// overloaded operator to be ambiguous.
+SPDY_EXPORT_PRIVATE std::ostream& operator<<(std::ostream& out,
+                                             SpdyKnownSettingsId id);
+
+// This operator is needed, because SpdyFrameType is an enum class,
+// therefore implicit conversion to underlying integer type is not allowed.
+SPDY_EXPORT_PRIVATE std::ostream& operator<<(std::ostream& out,
+                                             SpdyFrameType frame_type);
+
+using SettingsMap = std::map<SpdySettingsId, uint32_t>;
+
+// HTTP/2 error codes, RFC 7540 Section 7.
+enum SpdyErrorCode : uint32_t {
+  ERROR_CODE_NO_ERROR = 0x0,
+  ERROR_CODE_PROTOCOL_ERROR = 0x1,
+  ERROR_CODE_INTERNAL_ERROR = 0x2,
+  ERROR_CODE_FLOW_CONTROL_ERROR = 0x3,
+  ERROR_CODE_SETTINGS_TIMEOUT = 0x4,
+  ERROR_CODE_STREAM_CLOSED = 0x5,
+  ERROR_CODE_FRAME_SIZE_ERROR = 0x6,
+  ERROR_CODE_REFUSED_STREAM = 0x7,
+  ERROR_CODE_CANCEL = 0x8,
+  ERROR_CODE_COMPRESSION_ERROR = 0x9,
+  ERROR_CODE_CONNECT_ERROR = 0xa,
+  ERROR_CODE_ENHANCE_YOUR_CALM = 0xb,
+  ERROR_CODE_INADEQUATE_SECURITY = 0xc,
+  ERROR_CODE_HTTP_1_1_REQUIRED = 0xd,
+  ERROR_CODE_MAX = ERROR_CODE_HTTP_1_1_REQUIRED
+};
+
+// A SPDY priority is a number between 0 and 7 (inclusive).
+typedef uint8_t SpdyPriority;
+
+// Lowest and Highest here refer to SPDY priorities as described in
+// https://www.chromium.org/spdy/spdy-protocol/spdy-protocol-draft3-1#TOC-2.3.3-Stream-priority
+const SpdyPriority kV3HighestPriority = 0;
+const SpdyPriority kV3LowestPriority = 7;
+
+// Returns SPDY 3.x priority value clamped to the valid range of [0, 7].
+SPDY_EXPORT_PRIVATE SpdyPriority ClampSpdy3Priority(SpdyPriority priority);
+
+// HTTP/2 stream weights are integers in range [1, 256], as specified in RFC
+// 7540 section 5.3.2. Default stream weight is defined in section 5.3.5.
+const int kHttp2MinStreamWeight = 1;
+const int kHttp2MaxStreamWeight = 256;
+const int kHttp2DefaultStreamWeight = 16;
+
+// Returns HTTP/2 weight clamped to the valid range of [1, 256].
+SPDY_EXPORT_PRIVATE int ClampHttp2Weight(int weight);
+
+// Maps SPDY 3.x priority value in range [0, 7] to HTTP/2 weight value in range
+// [1, 256], where priority 0 (i.e. highest precedence) corresponds to maximum
+// weight 256 and priority 7 (lowest precedence) corresponds to minimum weight
+// 1.
+SPDY_EXPORT_PRIVATE int Spdy3PriorityToHttp2Weight(SpdyPriority priority);
+
+// Maps HTTP/2 weight value in range [1, 256] to SPDY 3.x priority value in
+// range [0, 7], where minimum weight 1 corresponds to priority 7 (lowest
+// precedence) and maximum weight 256 corresponds to priority 0 (highest
+// precedence).
+SPDY_EXPORT_PRIVATE SpdyPriority Http2WeightToSpdy3Priority(int weight);
+
+// Reserved ID for root stream of HTTP/2 stream dependency tree, as specified
+// in RFC 7540 section 5.3.1.
+const unsigned int kHttp2RootStreamId = 0;
+
+typedef uint64_t SpdyPingId;
+
+// Returns true if a given on-the-wire enumeration of a frame type is defined
+// in a standardized HTTP/2 specification, false otherwise.
+SPDY_EXPORT_PRIVATE bool IsDefinedFrameType(uint8_t frame_type_field);
+
+// Parses a frame type from an on-the-wire enumeration.
+// Behavior is undefined for invalid frame type fields; consumers should first
+// use IsValidFrameType() to verify validity of frame type fields.
+SPDY_EXPORT_PRIVATE SpdyFrameType ParseFrameType(uint8_t frame_type_field);
+
+// Serializes a frame type to the on-the-wire value.
+SPDY_EXPORT_PRIVATE uint8_t SerializeFrameType(SpdyFrameType frame_type);
+
+// (HTTP/2) All standard frame types except WINDOW_UPDATE are
+// (stream-specific xor connection-level). Returns false iff we know
+// the given frame type does not align with the given streamID.
+SPDY_EXPORT_PRIVATE bool IsValidHTTP2FrameStreamId(
+    SpdyStreamId current_frame_stream_id,
+    SpdyFrameType frame_type_field);
+
+// Serialize |frame_type| to string for logging/debugging.
+const char* FrameTypeToString(SpdyFrameType frame_type);
+
+// If |wire_setting_id| is the on-the-wire representation of a defined SETTINGS
+// parameter, parse it to |*setting_id| and return true.
+SPDY_EXPORT_PRIVATE bool ParseSettingsId(SpdySettingsId wire_setting_id,
+                                         SpdyKnownSettingsId* setting_id);
+
+// Returns a string representation of the |id| for logging/debugging. Returns
+// the |id| prefixed with "SETTINGS_UNKNOWN_" for unknown SETTINGS IDs. To parse
+// the |id| into a SpdyKnownSettingsId (if applicable), use ParseSettingsId().
+SPDY_EXPORT_PRIVATE SpdyString SettingsIdToString(SpdySettingsId id);
+
+// Parse |wire_error_code| to a SpdyErrorCode.
+// Treat unrecognized error codes as INTERNAL_ERROR
+// as recommended by the HTTP/2 specification.
+SPDY_EXPORT_PRIVATE SpdyErrorCode ParseErrorCode(uint32_t wire_error_code);
+
+// Serialize RST_STREAM or GOAWAY frame error code to string
+// for logging/debugging.
+const char* ErrorCodeToString(SpdyErrorCode error_code);
+
+// Minimum size of a frame, in octets.
+const size_t kFrameMinimumSize = kFrameHeaderSize;
+
+// Minimum frame size for variable size frame types (includes mandatory fields),
+// frame size for fixed size frames, in octets.
+
+const size_t kDataFrameMinimumSize = kFrameHeaderSize;
+const size_t kHeadersFrameMinimumSize = kFrameHeaderSize;
+// PRIORITY frame has stream_dependency (4 octets) and weight (1 octet) fields.
+const size_t kPriorityFrameSize = kFrameHeaderSize + 5;
+// RST_STREAM frame has error_code (4 octets) field.
+const size_t kRstStreamFrameSize = kFrameHeaderSize + 4;
+const size_t kSettingsFrameMinimumSize = kFrameHeaderSize;
+const size_t kSettingsOneSettingSize =
+    sizeof(uint32_t) + sizeof(SpdySettingsId);
+// PUSH_PROMISE frame has promised_stream_id (4 octet) field.
+const size_t kPushPromiseFrameMinimumSize = kFrameHeaderSize + 4;
+// PING frame has opaque_bytes (8 octet) field.
+const size_t kPingFrameSize = kFrameHeaderSize + 8;
+// GOAWAY frame has last_stream_id (4 octet) and error_code (4 octet) fields.
+const size_t kGoawayFrameMinimumSize = kFrameHeaderSize + 8;
+// WINDOW_UPDATE frame has window_size_increment (4 octet) field.
+const size_t kWindowUpdateFrameSize = kFrameHeaderSize + 4;
+const size_t kContinuationFrameMinimumSize = kFrameHeaderSize;
+// ALTSVC frame has origin_len (2 octets) field.
+const size_t kGetAltSvcFrameMinimumSize = kFrameHeaderSize + 2;
+
+// Maximum possible configurable size of a frame in octets.
+const size_t kMaxFrameSizeLimit = kSpdyMaxFrameSizeLimit + kFrameHeaderSize;
+// Size of a header block size field.
+const size_t kSizeOfSizeField = sizeof(uint32_t);
+// Per-header overhead for block size accounting in bytes.
+const size_t kPerHeaderOverhead = 32;
+// Initial window size for a stream in bytes.
+const int32_t kInitialStreamWindowSize = 64 * 1024 - 1;
+// Initial window size for a session in bytes.
+const int32_t kInitialSessionWindowSize = 64 * 1024 - 1;
+// The NPN string for HTTP2, "h2".
+extern const char* const kHttp2Npn;
+// An estimate size of the HPACK overhead for each header field. 1 bytes for
+// indexed literal, 1 bytes for key literal and length encoding, and 2 bytes for
+// value literal and length encoding.
+const size_t kPerHeaderHpackOverhead = 4;
+
+// Names of pseudo-headers defined for HTTP/2 requests.
+SPDY_EXPORT_PRIVATE extern const char* const kHttp2AuthorityHeader;
+SPDY_EXPORT_PRIVATE extern const char* const kHttp2MethodHeader;
+SPDY_EXPORT_PRIVATE extern const char* const kHttp2PathHeader;
+SPDY_EXPORT_PRIVATE extern const char* const kHttp2SchemeHeader;
+SPDY_EXPORT_PRIVATE extern const char* const kHttp2ProtocolHeader;
+
+// Name of pseudo-header defined for HTTP/2 responses.
+SPDY_EXPORT_PRIVATE extern const char* const kHttp2StatusHeader;
+
+SPDY_EXPORT_PRIVATE size_t GetNumberRequiredContinuationFrames(size_t size);
+
+// Variant type (i.e. tagged union) that is either a SPDY 3.x priority value,
+// or else an HTTP/2 stream dependency tuple {parent stream ID, weight,
+// exclusive bit}. Templated to allow for use by QUIC code; SPDY and HTTP/2
+// code should use the concrete type instantiation SpdyStreamPrecedence.
+template <typename StreamIdType>
+class StreamPrecedence {
+ public:
+  // Constructs instance that is a SPDY 3.x priority. Clamps priority value to
+  // the valid range [0, 7].
+  explicit StreamPrecedence(SpdyPriority priority)
+      : is_spdy3_priority_(true),
+        spdy3_priority_(ClampSpdy3Priority(priority)) {}
+
+  // Constructs instance that is an HTTP/2 stream weight, parent stream ID, and
+  // exclusive bit. Clamps stream weight to the valid range [1, 256].
+  StreamPrecedence(StreamIdType parent_id, int weight, bool is_exclusive)
+      : is_spdy3_priority_(false),
+        http2_stream_dependency_{parent_id, ClampHttp2Weight(weight),
+                                 is_exclusive} {}
+
+  // Intentionally copyable, to support pass by value.
+  StreamPrecedence(const StreamPrecedence& other) = default;
+  StreamPrecedence& operator=(const StreamPrecedence& other) = default;
+
+  // Returns true if this instance is a SPDY 3.x priority, or false if this
+  // instance is an HTTP/2 stream dependency.
+  bool is_spdy3_priority() const { return is_spdy3_priority_; }
+
+  // Returns SPDY 3.x priority value. If |is_spdy3_priority()| is true, this is
+  // the value provided at construction, clamped to the legal priority
+  // range. Otherwise, it is the HTTP/2 stream weight mapped to a SPDY 3.x
+  // priority value, where minimum weight 1 corresponds to priority 7 (lowest
+  // precedence) and maximum weight 256 corresponds to priority 0 (highest
+  // precedence).
+  SpdyPriority spdy3_priority() const {
+    return is_spdy3_priority_
+               ? spdy3_priority_
+               : Http2WeightToSpdy3Priority(http2_stream_dependency_.weight);
+  }
+
+  // Returns HTTP/2 parent stream ID. If |is_spdy3_priority()| is false, this is
+  // the value provided at construction, otherwise it is |kHttp2RootStreamId|.
+  StreamIdType parent_id() const {
+    return is_spdy3_priority_ ? kHttp2RootStreamId
+                              : http2_stream_dependency_.parent_id;
+  }
+
+  // Returns HTTP/2 stream weight. If |is_spdy3_priority()| is false, this is
+  // the value provided at construction, clamped to the legal weight
+  // range. Otherwise, it is the SPDY 3.x priority value mapped to an HTTP/2
+  // stream weight, where priority 0 (i.e. highest precedence) corresponds to
+  // maximum weight 256 and priority 7 (lowest precedence) corresponds to
+  // minimum weight 1.
+  int weight() const {
+    return is_spdy3_priority_ ? Spdy3PriorityToHttp2Weight(spdy3_priority_)
+                              : http2_stream_dependency_.weight;
+  }
+
+  // Returns HTTP/2 parent stream exclusivity. If |is_spdy3_priority()| is
+  // false, this is the value provided at construction, otherwise it is false.
+  bool is_exclusive() const {
+    return !is_spdy3_priority_ && http2_stream_dependency_.is_exclusive;
+  }
+
+  // Facilitates test assertions.
+  bool operator==(const StreamPrecedence& other) const {
+    if (is_spdy3_priority()) {
+      return other.is_spdy3_priority() &&
+             (spdy3_priority() == other.spdy3_priority());
+    } else {
+      return !other.is_spdy3_priority() && (parent_id() == other.parent_id()) &&
+             (weight() == other.weight()) &&
+             (is_exclusive() == other.is_exclusive());
+    }
+  }
+
+  bool operator!=(const StreamPrecedence& other) const {
+    return !(*this == other);
+  }
+
+ private:
+  struct Http2StreamDependency {
+    StreamIdType parent_id;
+    int weight;
+    bool is_exclusive;
+  };
+
+  bool is_spdy3_priority_;
+  union {
+    SpdyPriority spdy3_priority_;
+    Http2StreamDependency http2_stream_dependency_;
+  };
+};
+
+typedef StreamPrecedence<SpdyStreamId> SpdyStreamPrecedence;
+
+class SpdyFrameVisitor;
+
+// Intermediate representation for HTTP2 frames.
+class SPDY_EXPORT_PRIVATE SpdyFrameIR {
+ public:
+  virtual ~SpdyFrameIR() {}
+
+  virtual void Visit(SpdyFrameVisitor* visitor) const = 0;
+  virtual SpdyFrameType frame_type() const = 0;
+  SpdyStreamId stream_id() const { return stream_id_; }
+  virtual bool fin() const;
+  // Returns an estimate of the size of the serialized frame, without applying
+  // compression. May not be exact.
+  virtual size_t size() const = 0;
+
+  // Returns the number of bytes of flow control window that would be consumed
+  // by this frame if written to the wire.
+  virtual int flow_control_window_consumed() const;
+
+ protected:
+  SpdyFrameIR() : stream_id_(0) {}
+  explicit SpdyFrameIR(SpdyStreamId stream_id) : stream_id_(stream_id) {}
+  SpdyFrameIR(const SpdyFrameIR&) = delete;
+  SpdyFrameIR& operator=(const SpdyFrameIR&) = delete;
+
+ private:
+  SpdyStreamId stream_id_;
+};
+
+// Abstract class intended to be inherited by IRs that have the option of a FIN
+// flag.
+class SPDY_EXPORT_PRIVATE SpdyFrameWithFinIR : public SpdyFrameIR {
+ public:
+  ~SpdyFrameWithFinIR() override {}
+  bool fin() const override;
+  void set_fin(bool fin) { fin_ = fin; }
+
+ protected:
+  explicit SpdyFrameWithFinIR(SpdyStreamId stream_id)
+      : SpdyFrameIR(stream_id), fin_(false) {}
+  SpdyFrameWithFinIR(const SpdyFrameWithFinIR&) = delete;
+  SpdyFrameWithFinIR& operator=(const SpdyFrameWithFinIR&) = delete;
+
+ private:
+  bool fin_;
+};
+
+// Abstract class intended to be inherited by IRs that contain a header
+// block. Implies SpdyFrameWithFinIR.
+class SPDY_EXPORT_PRIVATE SpdyFrameWithHeaderBlockIR
+    : public SpdyFrameWithFinIR {
+ public:
+  ~SpdyFrameWithHeaderBlockIR() override;
+
+  const SpdyHeaderBlock& header_block() const { return header_block_; }
+  void set_header_block(SpdyHeaderBlock header_block) {
+    // Deep copy.
+    header_block_ = std::move(header_block);
+  }
+  void SetHeader(SpdyStringPiece name, SpdyStringPiece value) {
+    header_block_[name] = value;
+  }
+
+ protected:
+  SpdyFrameWithHeaderBlockIR(SpdyStreamId stream_id,
+                             SpdyHeaderBlock header_block);
+  SpdyFrameWithHeaderBlockIR(const SpdyFrameWithHeaderBlockIR&) = delete;
+  SpdyFrameWithHeaderBlockIR& operator=(const SpdyFrameWithHeaderBlockIR&) =
+      delete;
+
+ private:
+  SpdyHeaderBlock header_block_;
+};
+
+class SPDY_EXPORT_PRIVATE SpdyDataIR : public SpdyFrameWithFinIR {
+ public:
+  // Performs a deep copy on data.
+  SpdyDataIR(SpdyStreamId stream_id, SpdyStringPiece data);
+
+  // Performs a deep copy on data.
+  SpdyDataIR(SpdyStreamId stream_id, const char* data);
+
+  // Moves data into data_store_. Makes a copy if passed a non-movable string.
+  SpdyDataIR(SpdyStreamId stream_id, SpdyString data);
+
+  // Use in conjunction with SetDataShallow() for shallow-copy on data.
+  explicit SpdyDataIR(SpdyStreamId stream_id);
+  SpdyDataIR(const SpdyDataIR&) = delete;
+  SpdyDataIR& operator=(const SpdyDataIR&) = delete;
+
+  ~SpdyDataIR() override;
+
+  const char* data() const { return data_; }
+  size_t data_len() const { return data_len_; }
+
+  bool padded() const { return padded_; }
+
+  int padding_payload_len() const { return padding_payload_len_; }
+
+  void set_padding_len(int padding_len) {
+    DCHECK_GT(padding_len, 0);
+    DCHECK_LE(padding_len, kPaddingSizePerFrame);
+    padded_ = true;
+    // The pad field takes one octet on the wire.
+    padding_payload_len_ = padding_len - 1;
+  }
+
+  // Deep-copy of data (keep private copy).
+  void SetDataDeep(SpdyStringPiece data) {
+    data_store_ = SpdyMakeUnique<SpdyString>(data.data(), data.size());
+    data_ = data_store_->data();
+    data_len_ = data.size();
+  }
+
+  // Shallow-copy of data (do not keep private copy).
+  void SetDataShallow(SpdyStringPiece data) {
+    data_store_.reset();
+    data_ = data.data();
+    data_len_ = data.size();
+  }
+
+  // Use this method if we don't have a contiguous buffer and only
+  // need a length.
+  void SetDataShallow(size_t len) {
+    data_store_.reset();
+    data_ = nullptr;
+    data_len_ = len;
+  }
+
+  void Visit(SpdyFrameVisitor* visitor) const override;
+
+  SpdyFrameType frame_type() const override;
+
+  int flow_control_window_consumed() const override;
+
+  size_t size() const override;
+
+ private:
+  // Used to store data that this SpdyDataIR should own.
+  std::unique_ptr<SpdyString> data_store_;
+  const char* data_;
+  size_t data_len_;
+
+  bool padded_;
+  // padding_payload_len_ = desired padding length - len(padding length field).
+  int padding_payload_len_;
+};
+
+class SPDY_EXPORT_PRIVATE SpdyRstStreamIR : public SpdyFrameIR {
+ public:
+  SpdyRstStreamIR(SpdyStreamId stream_id, SpdyErrorCode error_code);
+  SpdyRstStreamIR(const SpdyRstStreamIR&) = delete;
+  SpdyRstStreamIR& operator=(const SpdyRstStreamIR&) = delete;
+
+  ~SpdyRstStreamIR() override;
+
+  SpdyErrorCode error_code() const { return error_code_; }
+  void set_error_code(SpdyErrorCode error_code) { error_code_ = error_code; }
+
+  void Visit(SpdyFrameVisitor* visitor) const override;
+
+  SpdyFrameType frame_type() const override;
+
+  size_t size() const override;
+
+ private:
+  SpdyErrorCode error_code_;
+};
+
+class SPDY_EXPORT_PRIVATE SpdySettingsIR : public SpdyFrameIR {
+ public:
+  SpdySettingsIR();
+  SpdySettingsIR(const SpdySettingsIR&) = delete;
+  SpdySettingsIR& operator=(const SpdySettingsIR&) = delete;
+  ~SpdySettingsIR() override;
+
+  // Overwrites as appropriate.
+  const SettingsMap& values() const { return values_; }
+  void AddSetting(SpdySettingsId id, int32_t value) { values_[id] = value; }
+
+  bool is_ack() const { return is_ack_; }
+  void set_is_ack(bool is_ack) { is_ack_ = is_ack; }
+
+  void Visit(SpdyFrameVisitor* visitor) const override;
+
+  SpdyFrameType frame_type() const override;
+
+  size_t size() const override;
+
+ private:
+  SettingsMap values_;
+  bool is_ack_;
+};
+
+class SPDY_EXPORT_PRIVATE SpdyPingIR : public SpdyFrameIR {
+ public:
+  explicit SpdyPingIR(SpdyPingId id) : id_(id), is_ack_(false) {}
+  SpdyPingIR(const SpdyPingIR&) = delete;
+  SpdyPingIR& operator=(const SpdyPingIR&) = delete;
+  SpdyPingId id() const { return id_; }
+
+  bool is_ack() const { return is_ack_; }
+  void set_is_ack(bool is_ack) { is_ack_ = is_ack; }
+
+  void Visit(SpdyFrameVisitor* visitor) const override;
+
+  SpdyFrameType frame_type() const override;
+
+  size_t size() const override;
+
+ private:
+  SpdyPingId id_;
+  bool is_ack_;
+};
+
+class SPDY_EXPORT_PRIVATE SpdyGoAwayIR : public SpdyFrameIR {
+ public:
+  // References description, doesn't copy it, so description must outlast
+  // this SpdyGoAwayIR.
+  SpdyGoAwayIR(SpdyStreamId last_good_stream_id,
+               SpdyErrorCode error_code,
+               SpdyStringPiece description);
+
+  // References description, doesn't copy it, so description must outlast
+  // this SpdyGoAwayIR.
+  SpdyGoAwayIR(SpdyStreamId last_good_stream_id,
+               SpdyErrorCode error_code,
+               const char* description);
+
+  // Moves description into description_store_, so caller doesn't need to
+  // keep description live after constructing this SpdyGoAwayIR.
+  SpdyGoAwayIR(SpdyStreamId last_good_stream_id,
+               SpdyErrorCode error_code,
+               SpdyString description);
+  SpdyGoAwayIR(const SpdyGoAwayIR&) = delete;
+  SpdyGoAwayIR& operator=(const SpdyGoAwayIR&) = delete;
+
+  ~SpdyGoAwayIR() override;
+
+  SpdyStreamId last_good_stream_id() const { return last_good_stream_id_; }
+  void set_last_good_stream_id(SpdyStreamId last_good_stream_id) {
+    DCHECK_EQ(0u, last_good_stream_id & ~kStreamIdMask);
+    last_good_stream_id_ = last_good_stream_id;
+  }
+  SpdyErrorCode error_code() const { return error_code_; }
+  void set_error_code(SpdyErrorCode error_code) {
+    // TODO(hkhalil): Check valid ranges of error_code?
+    error_code_ = error_code;
+  }
+
+  const SpdyStringPiece& description() const { return description_; }
+
+  void Visit(SpdyFrameVisitor* visitor) const override;
+
+  SpdyFrameType frame_type() const override;
+
+  size_t size() const override;
+
+ private:
+  SpdyStreamId last_good_stream_id_;
+  SpdyErrorCode error_code_;
+  const SpdyString description_store_;
+  const SpdyStringPiece description_;
+};
+
+class SPDY_EXPORT_PRIVATE SpdyHeadersIR : public SpdyFrameWithHeaderBlockIR {
+ public:
+  explicit SpdyHeadersIR(SpdyStreamId stream_id)
+      : SpdyHeadersIR(stream_id, SpdyHeaderBlock()) {}
+  SpdyHeadersIR(SpdyStreamId stream_id, SpdyHeaderBlock header_block)
+      : SpdyFrameWithHeaderBlockIR(stream_id, std::move(header_block)) {}
+  SpdyHeadersIR(const SpdyHeadersIR&) = delete;
+  SpdyHeadersIR& operator=(const SpdyHeadersIR&) = delete;
+
+  void Visit(SpdyFrameVisitor* visitor) const override;
+
+  SpdyFrameType frame_type() const override;
+
+  size_t size() const override;
+
+  bool has_priority() const { return has_priority_; }
+  void set_has_priority(bool has_priority) { has_priority_ = has_priority; }
+  int weight() const { return weight_; }
+  void set_weight(int weight) { weight_ = weight; }
+  SpdyStreamId parent_stream_id() const { return parent_stream_id_; }
+  void set_parent_stream_id(SpdyStreamId id) { parent_stream_id_ = id; }
+  bool exclusive() const { return exclusive_; }
+  void set_exclusive(bool exclusive) { exclusive_ = exclusive; }
+  bool padded() const { return padded_; }
+  int padding_payload_len() const { return padding_payload_len_; }
+  void set_padding_len(int padding_len) {
+    DCHECK_GT(padding_len, 0);
+    DCHECK_LE(padding_len, kPaddingSizePerFrame);
+    padded_ = true;
+    // The pad field takes one octet on the wire.
+    padding_payload_len_ = padding_len - 1;
+  }
+
+ private:
+  bool has_priority_ = false;
+  int weight_ = kHttp2DefaultStreamWeight;
+  SpdyStreamId parent_stream_id_ = 0;
+  bool exclusive_ = false;
+  bool padded_ = false;
+  int padding_payload_len_ = 0;
+};
+
+class SPDY_EXPORT_PRIVATE SpdyWindowUpdateIR : public SpdyFrameIR {
+ public:
+  SpdyWindowUpdateIR(SpdyStreamId stream_id, int32_t delta)
+      : SpdyFrameIR(stream_id) {
+    set_delta(delta);
+  }
+  SpdyWindowUpdateIR(const SpdyWindowUpdateIR&) = delete;
+  SpdyWindowUpdateIR& operator=(const SpdyWindowUpdateIR&) = delete;
+
+  int32_t delta() const { return delta_; }
+  void set_delta(int32_t delta) {
+    DCHECK_LE(0, delta);
+    DCHECK_LE(delta, kSpdyMaximumWindowSize);
+    delta_ = delta;
+  }
+
+  void Visit(SpdyFrameVisitor* visitor) const override;
+
+  SpdyFrameType frame_type() const override;
+
+  size_t size() const override;
+
+ private:
+  int32_t delta_;
+};
+
+class SPDY_EXPORT_PRIVATE SpdyPushPromiseIR
+    : public SpdyFrameWithHeaderBlockIR {
+ public:
+  SpdyPushPromiseIR(SpdyStreamId stream_id, SpdyStreamId promised_stream_id)
+      : SpdyPushPromiseIR(stream_id, promised_stream_id, SpdyHeaderBlock()) {}
+  SpdyPushPromiseIR(SpdyStreamId stream_id,
+                    SpdyStreamId promised_stream_id,
+                    SpdyHeaderBlock header_block)
+      : SpdyFrameWithHeaderBlockIR(stream_id, std::move(header_block)),
+        promised_stream_id_(promised_stream_id),
+        padded_(false),
+        padding_payload_len_(0) {}
+  SpdyPushPromiseIR(const SpdyPushPromiseIR&) = delete;
+  SpdyPushPromiseIR& operator=(const SpdyPushPromiseIR&) = delete;
+  SpdyStreamId promised_stream_id() const { return promised_stream_id_; }
+
+  void Visit(SpdyFrameVisitor* visitor) const override;
+
+  SpdyFrameType frame_type() const override;
+
+  size_t size() const override;
+
+  bool padded() const { return padded_; }
+  int padding_payload_len() const { return padding_payload_len_; }
+  void set_padding_len(int padding_len) {
+    DCHECK_GT(padding_len, 0);
+    DCHECK_LE(padding_len, kPaddingSizePerFrame);
+    padded_ = true;
+    // The pad field takes one octet on the wire.
+    padding_payload_len_ = padding_len - 1;
+  }
+
+ private:
+  SpdyStreamId promised_stream_id_;
+
+  bool padded_;
+  int padding_payload_len_;
+};
+
+class SPDY_EXPORT_PRIVATE SpdyContinuationIR : public SpdyFrameIR {
+ public:
+  explicit SpdyContinuationIR(SpdyStreamId stream_id);
+  SpdyContinuationIR(const SpdyContinuationIR&) = delete;
+  SpdyContinuationIR& operator=(const SpdyContinuationIR&) = delete;
+  ~SpdyContinuationIR() override;
+
+  void Visit(SpdyFrameVisitor* visitor) const override;
+
+  SpdyFrameType frame_type() const override;
+
+  bool end_headers() const { return end_headers_; }
+  void set_end_headers(bool end_headers) { end_headers_ = end_headers; }
+  const SpdyString& encoding() const { return *encoding_; }
+  void take_encoding(std::unique_ptr<SpdyString> encoding) {
+    encoding_ = std::move(encoding);
+  }
+  size_t size() const override;
+
+ private:
+  std::unique_ptr<SpdyString> encoding_;
+  bool end_headers_;
+};
+
+class SPDY_EXPORT_PRIVATE SpdyAltSvcIR : public SpdyFrameIR {
+ public:
+  explicit SpdyAltSvcIR(SpdyStreamId stream_id);
+  SpdyAltSvcIR(const SpdyAltSvcIR&) = delete;
+  SpdyAltSvcIR& operator=(const SpdyAltSvcIR&) = delete;
+  ~SpdyAltSvcIR() override;
+
+  SpdyString origin() const { return origin_; }
+  const SpdyAltSvcWireFormat::AlternativeServiceVector& altsvc_vector() const {
+    return altsvc_vector_;
+  }
+
+  void set_origin(SpdyString origin) { origin_ = std::move(origin); }
+  void add_altsvc(const SpdyAltSvcWireFormat::AlternativeService& altsvc) {
+    altsvc_vector_.push_back(altsvc);
+  }
+
+  void Visit(SpdyFrameVisitor* visitor) const override;
+
+  SpdyFrameType frame_type() const override;
+
+  size_t size() const override;
+
+ private:
+  SpdyString origin_;
+  SpdyAltSvcWireFormat::AlternativeServiceVector altsvc_vector_;
+};
+
+class SPDY_EXPORT_PRIVATE SpdyPriorityIR : public SpdyFrameIR {
+ public:
+  SpdyPriorityIR(SpdyStreamId stream_id,
+                 SpdyStreamId parent_stream_id,
+                 int weight,
+                 bool exclusive)
+      : SpdyFrameIR(stream_id),
+        parent_stream_id_(parent_stream_id),
+        weight_(weight),
+        exclusive_(exclusive) {}
+  SpdyPriorityIR(const SpdyPriorityIR&) = delete;
+  SpdyPriorityIR& operator=(const SpdyPriorityIR&) = delete;
+  SpdyStreamId parent_stream_id() const { return parent_stream_id_; }
+  int weight() const { return weight_; }
+  bool exclusive() const { return exclusive_; }
+
+  void Visit(SpdyFrameVisitor* visitor) const override;
+
+  SpdyFrameType frame_type() const override;
+
+  size_t size() const override;
+
+ private:
+  SpdyStreamId parent_stream_id_;
+  int weight_;
+  bool exclusive_;
+};
+
+// Represents a frame of unrecognized type.
+class SPDY_EXPORT_PRIVATE SpdyUnknownIR : public SpdyFrameIR {
+ public:
+  SpdyUnknownIR(SpdyStreamId stream_id,
+                uint8_t type,
+                uint8_t flags,
+                SpdyString payload)
+      : SpdyFrameIR(stream_id),
+        type_(type),
+        flags_(flags),
+        length_(payload.size()),
+        payload_(std::move(payload)) {}
+  SpdyUnknownIR(const SpdyUnknownIR&) = delete;
+  SpdyUnknownIR& operator=(const SpdyUnknownIR&) = delete;
+  uint8_t type() const { return type_; }
+  uint8_t flags() const { return flags_; }
+  size_t length() const { return length_; }
+  const SpdyString& payload() const { return payload_; }
+
+  void Visit(SpdyFrameVisitor* visitor) const override;
+
+  SpdyFrameType frame_type() const override;
+
+  int flow_control_window_consumed() const override;
+
+  size_t size() const override;
+
+ protected:
+  // Allows subclasses to overwrite the default payload length.
+  void set_length(size_t length) { length_ = length; }
+
+ private:
+  uint8_t type_;
+  uint8_t flags_;
+  size_t length_;
+  const SpdyString payload_;
+};
+
+class SPDY_EXPORT_PRIVATE SpdySerializedFrame {
+ public:
+  SpdySerializedFrame()
+      : frame_(const_cast<char*>("")), size_(0), owns_buffer_(false) {}
+
+  // Create a valid SpdySerializedFrame using a pre-created buffer.
+  // If |owns_buffer| is true, this class takes ownership of the buffer and will
+  // delete it on cleanup.  The buffer must have been created using new char[].
+  // If |owns_buffer| is false, the caller retains ownership of the buffer and
+  // is responsible for making sure the buffer outlives this frame.  In other
+  // words, this class does NOT create a copy of the buffer.
+  SpdySerializedFrame(char* data, size_t size, bool owns_buffer)
+      : frame_(data), size_(size), owns_buffer_(owns_buffer) {}
+
+  SpdySerializedFrame(SpdySerializedFrame&& other)
+      : frame_(other.frame_),
+        size_(other.size_),
+        owns_buffer_(other.owns_buffer_) {
+    // |other| is no longer responsible for the buffer.
+    other.owns_buffer_ = false;
+  }
+  SpdySerializedFrame(const SpdySerializedFrame&) = delete;
+  SpdySerializedFrame& operator=(const SpdySerializedFrame&) = delete;
+
+  SpdySerializedFrame& operator=(SpdySerializedFrame&& other) {
+    // Free buffer if necessary.
+    if (owns_buffer_) {
+      delete[] frame_;
+    }
+    // Take over |other|.
+    frame_ = other.frame_;
+    size_ = other.size_;
+    owns_buffer_ = other.owns_buffer_;
+    // |other| is no longer responsible for the buffer.
+    other.owns_buffer_ = false;
+    return *this;
+  }
+
+  ~SpdySerializedFrame() {
+    if (owns_buffer_) {
+      delete[] frame_;
+    }
+  }
+
+  // Provides access to the frame bytes, which is a buffer containing the frame
+  // packed as expected for sending over the wire.
+  char* data() const { return frame_; }
+
+  // Returns the actual size of the underlying buffer.
+  size_t size() const { return size_; }
+
+  // Returns a buffer containing the contents of the frame, of which the caller
+  // takes ownership, and clears this SpdySerializedFrame.
+  char* ReleaseBuffer() {
+    char* buffer;
+    if (owns_buffer_) {
+      // If the buffer is owned, relinquish ownership to the caller.
+      buffer = frame_;
+      owns_buffer_ = false;
+    } else {
+      // Otherwise, we need to make a copy to give to the caller.
+      buffer = new char[size_];
+      memcpy(buffer, frame_, size_);
+    }
+    *this = SpdySerializedFrame();
+    return buffer;
+  }
+
+  // Returns the estimate of dynamically allocated memory in bytes.
+  size_t EstimateMemoryUsage() const { return owns_buffer_ ? size_ : 0; }
+
+ protected:
+  char* frame_;
+
+ private:
+  size_t size_;
+  bool owns_buffer_;
+};
+
+// This interface is for classes that want to process SpdyFrameIRs without
+// having to know what type they are.  An instance of this interface can be
+// passed to a SpdyFrameIR's Visit method, and the appropriate type-specific
+// method of this class will be called.
+class SPDY_EXPORT_PRIVATE SpdyFrameVisitor {
+ public:
+  virtual void VisitRstStream(const SpdyRstStreamIR& rst_stream) = 0;
+  virtual void VisitSettings(const SpdySettingsIR& settings) = 0;
+  virtual void VisitPing(const SpdyPingIR& ping) = 0;
+  virtual void VisitGoAway(const SpdyGoAwayIR& goaway) = 0;
+  virtual void VisitHeaders(const SpdyHeadersIR& headers) = 0;
+  virtual void VisitWindowUpdate(const SpdyWindowUpdateIR& window_update) = 0;
+  virtual void VisitPushPromise(const SpdyPushPromiseIR& push_promise) = 0;
+  virtual void VisitContinuation(const SpdyContinuationIR& continuation) = 0;
+  virtual void VisitAltSvc(const SpdyAltSvcIR& altsvc) = 0;
+  virtual void VisitPriority(const SpdyPriorityIR& priority) = 0;
+  virtual void VisitData(const SpdyDataIR& data) = 0;
+  virtual void VisitUnknown(const SpdyUnknownIR& unknown) {
+    // TODO(birenroy): make abstract.
+  }
+
+ protected:
+  SpdyFrameVisitor() {}
+  SpdyFrameVisitor(const SpdyFrameVisitor&) = delete;
+  SpdyFrameVisitor& operator=(const SpdyFrameVisitor&) = delete;
+  virtual ~SpdyFrameVisitor() {}
+};
+
+// Optionally, and in addition to SpdyFramerVisitorInterface, a class supporting
+// SpdyFramerDebugVisitorInterface may be used in conjunction with SpdyFramer in
+// order to extract debug/internal information about the SpdyFramer as it
+// operates.
+//
+// Most HTTP2 implementations need not bother with this interface at all.
+class SPDY_EXPORT_PRIVATE SpdyFramerDebugVisitorInterface {
+ public:
+  virtual ~SpdyFramerDebugVisitorInterface() {}
+
+  // Called after compressing a frame with a payload of
+  // a list of name-value pairs.
+  // |payload_len| is the uncompressed payload size.
+  // |frame_len| is the compressed frame size.
+  virtual void OnSendCompressedFrame(SpdyStreamId stream_id,
+                                     SpdyFrameType type,
+                                     size_t payload_len,
+                                     size_t frame_len) {}
+
+  // Called when a frame containing a compressed payload of
+  // name-value pairs is received.
+  // |frame_len| is the compressed frame size.
+  virtual void OnReceiveCompressedFrame(SpdyStreamId stream_id,
+                                        SpdyFrameType type,
+                                        size_t frame_len) {}
+};
+
+// Calculates the number of bytes required to serialize a SpdyHeadersIR, not
+// including the bytes to be used for the encoded header set.
+size_t GetHeaderFrameSizeSansBlock(const SpdyHeadersIR& header_ir);
+
+// Calculates the number of bytes required to serialize a SpdyPushPromiseIR,
+// not including the bytes to be used for the encoded header set.
+size_t GetPushPromiseFrameSizeSansBlock(
+    const SpdyPushPromiseIR& push_promise_ir);
+
+}  // namespace spdy
+
+#endif  // QUICHE_SPDY_CORE_SPDY_PROTOCOL_H_
diff --git a/spdy/core/spdy_protocol_test.cc b/spdy/core/spdy_protocol_test.cc
new file mode 100644
index 0000000..09a56cb
--- /dev/null
+++ b/spdy/core/spdy_protocol_test.cc
@@ -0,0 +1,270 @@
+// Copyright (c) 2012 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "net/third_party/quiche/src/spdy/core/spdy_protocol.h"
+
+#include <iostream>
+#include <limits>
+#include <memory>
+
+#include "testing/gtest/include/gtest/gtest.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_bitmasks.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_test_utils.h"
+
+namespace spdy {
+
+std::ostream& operator<<(std::ostream& os,
+                         const SpdyStreamPrecedence precedence) {
+  if (precedence.is_spdy3_priority()) {
+    os << "SpdyStreamPrecedence[spdy3_priority=" << precedence.spdy3_priority()
+       << "]";
+  } else {
+    os << "SpdyStreamPrecedence[parent_id=" << precedence.parent_id()
+       << ", weight=" << precedence.weight()
+       << ", is_exclusive=" << precedence.is_exclusive() << "]";
+  }
+  return os;
+}
+
+namespace test {
+
+TEST(SpdyProtocolTest, ClampSpdy3Priority) {
+  EXPECT_SPDY_BUG(EXPECT_EQ(7, ClampSpdy3Priority(8)), "Invalid priority: 8");
+  EXPECT_EQ(kV3LowestPriority, ClampSpdy3Priority(kV3LowestPriority));
+  EXPECT_EQ(kV3HighestPriority, ClampSpdy3Priority(kV3HighestPriority));
+}
+
+TEST(SpdyProtocolTest, ClampHttp2Weight) {
+  EXPECT_SPDY_BUG(EXPECT_EQ(kHttp2MinStreamWeight, ClampHttp2Weight(0)),
+                  "Invalid weight: 0");
+  EXPECT_SPDY_BUG(EXPECT_EQ(kHttp2MaxStreamWeight, ClampHttp2Weight(300)),
+                  "Invalid weight: 300");
+  EXPECT_EQ(kHttp2MinStreamWeight, ClampHttp2Weight(kHttp2MinStreamWeight));
+  EXPECT_EQ(kHttp2MaxStreamWeight, ClampHttp2Weight(kHttp2MaxStreamWeight));
+}
+
+TEST(SpdyProtocolTest, Spdy3PriorityToHttp2Weight) {
+  EXPECT_EQ(256, Spdy3PriorityToHttp2Weight(0));
+  EXPECT_EQ(220, Spdy3PriorityToHttp2Weight(1));
+  EXPECT_EQ(183, Spdy3PriorityToHttp2Weight(2));
+  EXPECT_EQ(147, Spdy3PriorityToHttp2Weight(3));
+  EXPECT_EQ(110, Spdy3PriorityToHttp2Weight(4));
+  EXPECT_EQ(74, Spdy3PriorityToHttp2Weight(5));
+  EXPECT_EQ(37, Spdy3PriorityToHttp2Weight(6));
+  EXPECT_EQ(1, Spdy3PriorityToHttp2Weight(7));
+}
+
+TEST(SpdyProtocolTest, Http2WeightToSpdy3Priority) {
+  EXPECT_EQ(0u, Http2WeightToSpdy3Priority(256));
+  EXPECT_EQ(0u, Http2WeightToSpdy3Priority(221));
+  EXPECT_EQ(1u, Http2WeightToSpdy3Priority(220));
+  EXPECT_EQ(1u, Http2WeightToSpdy3Priority(184));
+  EXPECT_EQ(2u, Http2WeightToSpdy3Priority(183));
+  EXPECT_EQ(2u, Http2WeightToSpdy3Priority(148));
+  EXPECT_EQ(3u, Http2WeightToSpdy3Priority(147));
+  EXPECT_EQ(3u, Http2WeightToSpdy3Priority(111));
+  EXPECT_EQ(4u, Http2WeightToSpdy3Priority(110));
+  EXPECT_EQ(4u, Http2WeightToSpdy3Priority(75));
+  EXPECT_EQ(5u, Http2WeightToSpdy3Priority(74));
+  EXPECT_EQ(5u, Http2WeightToSpdy3Priority(38));
+  EXPECT_EQ(6u, Http2WeightToSpdy3Priority(37));
+  EXPECT_EQ(6u, Http2WeightToSpdy3Priority(2));
+  EXPECT_EQ(7u, Http2WeightToSpdy3Priority(1));
+}
+
+TEST(SpdyProtocolTest, IsValidHTTP2FrameStreamId) {
+  // Stream-specific frames must have non-zero stream ids
+  EXPECT_TRUE(IsValidHTTP2FrameStreamId(1, SpdyFrameType::DATA));
+  EXPECT_FALSE(IsValidHTTP2FrameStreamId(0, SpdyFrameType::DATA));
+  EXPECT_TRUE(IsValidHTTP2FrameStreamId(1, SpdyFrameType::HEADERS));
+  EXPECT_FALSE(IsValidHTTP2FrameStreamId(0, SpdyFrameType::HEADERS));
+  EXPECT_TRUE(IsValidHTTP2FrameStreamId(1, SpdyFrameType::PRIORITY));
+  EXPECT_FALSE(IsValidHTTP2FrameStreamId(0, SpdyFrameType::PRIORITY));
+  EXPECT_TRUE(IsValidHTTP2FrameStreamId(1, SpdyFrameType::RST_STREAM));
+  EXPECT_FALSE(IsValidHTTP2FrameStreamId(0, SpdyFrameType::RST_STREAM));
+  EXPECT_TRUE(IsValidHTTP2FrameStreamId(1, SpdyFrameType::CONTINUATION));
+  EXPECT_FALSE(IsValidHTTP2FrameStreamId(0, SpdyFrameType::CONTINUATION));
+  EXPECT_TRUE(IsValidHTTP2FrameStreamId(1, SpdyFrameType::PUSH_PROMISE));
+  EXPECT_FALSE(IsValidHTTP2FrameStreamId(0, SpdyFrameType::PUSH_PROMISE));
+
+  // Connection-level frames must have zero stream ids
+  EXPECT_FALSE(IsValidHTTP2FrameStreamId(1, SpdyFrameType::GOAWAY));
+  EXPECT_TRUE(IsValidHTTP2FrameStreamId(0, SpdyFrameType::GOAWAY));
+  EXPECT_FALSE(IsValidHTTP2FrameStreamId(1, SpdyFrameType::SETTINGS));
+  EXPECT_TRUE(IsValidHTTP2FrameStreamId(0, SpdyFrameType::SETTINGS));
+  EXPECT_FALSE(IsValidHTTP2FrameStreamId(1, SpdyFrameType::PING));
+  EXPECT_TRUE(IsValidHTTP2FrameStreamId(0, SpdyFrameType::PING));
+
+  // Frames that are neither stream-specific nor connection-level
+  // should not have their stream id declared invalid
+  EXPECT_TRUE(IsValidHTTP2FrameStreamId(1, SpdyFrameType::WINDOW_UPDATE));
+  EXPECT_TRUE(IsValidHTTP2FrameStreamId(0, SpdyFrameType::WINDOW_UPDATE));
+}
+
+TEST(SpdyProtocolTest, ParseSettingsId) {
+  SpdyKnownSettingsId setting_id;
+  EXPECT_FALSE(ParseSettingsId(0, &setting_id));
+  EXPECT_TRUE(ParseSettingsId(1, &setting_id));
+  EXPECT_EQ(SETTINGS_HEADER_TABLE_SIZE, setting_id);
+  EXPECT_TRUE(ParseSettingsId(2, &setting_id));
+  EXPECT_EQ(SETTINGS_ENABLE_PUSH, setting_id);
+  EXPECT_TRUE(ParseSettingsId(3, &setting_id));
+  EXPECT_EQ(SETTINGS_MAX_CONCURRENT_STREAMS, setting_id);
+  EXPECT_TRUE(ParseSettingsId(4, &setting_id));
+  EXPECT_EQ(SETTINGS_INITIAL_WINDOW_SIZE, setting_id);
+  EXPECT_TRUE(ParseSettingsId(5, &setting_id));
+  EXPECT_EQ(SETTINGS_MAX_FRAME_SIZE, setting_id);
+  EXPECT_TRUE(ParseSettingsId(6, &setting_id));
+  EXPECT_EQ(SETTINGS_MAX_HEADER_LIST_SIZE, setting_id);
+  EXPECT_FALSE(ParseSettingsId(7, &setting_id));
+  EXPECT_TRUE(ParseSettingsId(8, &setting_id));
+  EXPECT_EQ(SETTINGS_ENABLE_CONNECT_PROTOCOL, setting_id);
+  EXPECT_FALSE(ParseSettingsId(9, &setting_id));
+  EXPECT_FALSE(ParseSettingsId(0xFF44, &setting_id));
+  EXPECT_TRUE(ParseSettingsId(0xFF45, &setting_id));
+  EXPECT_EQ(SETTINGS_EXPERIMENT_SCHEDULER, setting_id);
+  EXPECT_FALSE(ParseSettingsId(0xFF46, &setting_id));
+}
+
+TEST(SpdyProtocolTest, SettingsIdToString) {
+  struct {
+    SpdySettingsId setting_id;
+    const SpdyString expected_string;
+  } test_cases[] = {
+      {0, "SETTINGS_UNKNOWN_0"},
+      {SETTINGS_HEADER_TABLE_SIZE, "SETTINGS_HEADER_TABLE_SIZE"},
+      {SETTINGS_ENABLE_PUSH, "SETTINGS_ENABLE_PUSH"},
+      {SETTINGS_MAX_CONCURRENT_STREAMS, "SETTINGS_MAX_CONCURRENT_STREAMS"},
+      {SETTINGS_INITIAL_WINDOW_SIZE, "SETTINGS_INITIAL_WINDOW_SIZE"},
+      {SETTINGS_MAX_FRAME_SIZE, "SETTINGS_MAX_FRAME_SIZE"},
+      {SETTINGS_MAX_HEADER_LIST_SIZE, "SETTINGS_MAX_HEADER_LIST_SIZE"},
+      {7, "SETTINGS_UNKNOWN_7"},
+      {SETTINGS_ENABLE_CONNECT_PROTOCOL, "SETTINGS_ENABLE_CONNECT_PROTOCOL"},
+      {9, "SETTINGS_UNKNOWN_9"},
+      {0xFF44, "SETTINGS_UNKNOWN_ff44"},
+      {0xFF45, "SETTINGS_EXPERIMENT_SCHEDULER"},
+      {0xFF46, "SETTINGS_UNKNOWN_ff46"}};
+  for (auto test_case : test_cases) {
+    EXPECT_EQ(test_case.expected_string,
+              SettingsIdToString(test_case.setting_id));
+  }
+}
+
+TEST(SpdyStreamPrecedenceTest, Basic) {
+  SpdyStreamPrecedence spdy3_prec(2);
+  EXPECT_TRUE(spdy3_prec.is_spdy3_priority());
+  EXPECT_EQ(2, spdy3_prec.spdy3_priority());
+  EXPECT_EQ(kHttp2RootStreamId, spdy3_prec.parent_id());
+  EXPECT_EQ(Spdy3PriorityToHttp2Weight(2), spdy3_prec.weight());
+  EXPECT_FALSE(spdy3_prec.is_exclusive());
+
+  for (bool is_exclusive : {true, false}) {
+    SpdyStreamPrecedence h2_prec(7, 123, is_exclusive);
+    EXPECT_FALSE(h2_prec.is_spdy3_priority());
+    EXPECT_EQ(Http2WeightToSpdy3Priority(123), h2_prec.spdy3_priority());
+    EXPECT_EQ(7u, h2_prec.parent_id());
+    EXPECT_EQ(123, h2_prec.weight());
+    EXPECT_EQ(is_exclusive, h2_prec.is_exclusive());
+  }
+}
+
+TEST(SpdyStreamPrecedenceTest, Clamping) {
+  EXPECT_SPDY_BUG(EXPECT_EQ(7, SpdyStreamPrecedence(8).spdy3_priority()),
+                  "Invalid priority: 8");
+  EXPECT_SPDY_BUG(EXPECT_EQ(kHttp2MinStreamWeight,
+                            SpdyStreamPrecedence(3, 0, false).weight()),
+                  "Invalid weight: 0");
+  EXPECT_SPDY_BUG(EXPECT_EQ(kHttp2MaxStreamWeight,
+                            SpdyStreamPrecedence(3, 300, false).weight()),
+                  "Invalid weight: 300");
+}
+
+TEST(SpdyStreamPrecedenceTest, Copying) {
+  SpdyStreamPrecedence prec1(3);
+  SpdyStreamPrecedence copy1(prec1);
+  EXPECT_TRUE(copy1.is_spdy3_priority());
+  EXPECT_EQ(3, copy1.spdy3_priority());
+
+  SpdyStreamPrecedence prec2(4, 5, true);
+  SpdyStreamPrecedence copy2(prec2);
+  EXPECT_FALSE(copy2.is_spdy3_priority());
+  EXPECT_EQ(4u, copy2.parent_id());
+  EXPECT_EQ(5, copy2.weight());
+  EXPECT_TRUE(copy2.is_exclusive());
+
+  copy1 = prec2;
+  EXPECT_FALSE(copy1.is_spdy3_priority());
+  EXPECT_EQ(4u, copy1.parent_id());
+  EXPECT_EQ(5, copy1.weight());
+  EXPECT_TRUE(copy1.is_exclusive());
+
+  copy2 = prec1;
+  EXPECT_TRUE(copy2.is_spdy3_priority());
+  EXPECT_EQ(3, copy2.spdy3_priority());
+}
+
+TEST(SpdyStreamPrecedenceTest, Equals) {
+  EXPECT_EQ(SpdyStreamPrecedence(3), SpdyStreamPrecedence(3));
+  EXPECT_NE(SpdyStreamPrecedence(3), SpdyStreamPrecedence(4));
+
+  EXPECT_EQ(SpdyStreamPrecedence(1, 2, false),
+            SpdyStreamPrecedence(1, 2, false));
+  EXPECT_NE(SpdyStreamPrecedence(1, 2, false),
+            SpdyStreamPrecedence(2, 2, false));
+  EXPECT_NE(SpdyStreamPrecedence(1, 2, false),
+            SpdyStreamPrecedence(1, 3, false));
+  EXPECT_NE(SpdyStreamPrecedence(1, 2, false),
+            SpdyStreamPrecedence(1, 2, true));
+
+  SpdyStreamPrecedence spdy3_prec(3);
+  SpdyStreamPrecedence h2_prec(spdy3_prec.parent_id(), spdy3_prec.weight(),
+                               spdy3_prec.is_exclusive());
+  EXPECT_NE(spdy3_prec, h2_prec);
+}
+
+TEST(SpdyDataIRTest, Construct) {
+  // Confirm that it makes a string of zero length from a
+  // SpdyStringPiece(nullptr).
+  SpdyStringPiece s1;
+  SpdyDataIR d1(/* stream_id = */ 1, s1);
+  EXPECT_EQ(0u, d1.data_len());
+  EXPECT_NE(nullptr, d1.data());
+
+  // Confirms makes a copy of char array.
+  const char s2[] = "something";
+  SpdyDataIR d2(/* stream_id = */ 2, s2);
+  EXPECT_EQ(SpdyStringPiece(d2.data(), d2.data_len()), s2);
+  EXPECT_NE(SpdyStringPiece(d1.data(), d1.data_len()), s2);
+  EXPECT_EQ((int)d1.data_len(), d1.flow_control_window_consumed());
+
+  // Confirm copies a const string.
+  const SpdyString foo = "foo";
+  SpdyDataIR d3(/* stream_id = */ 3, foo);
+  EXPECT_EQ(foo, d3.data());
+  EXPECT_EQ((int)d3.data_len(), d3.flow_control_window_consumed());
+
+  // Confirm copies a non-const string.
+  SpdyString bar = "bar";
+  SpdyDataIR d4(/* stream_id = */ 4, bar);
+  EXPECT_EQ("bar", bar);
+  EXPECT_EQ("bar", SpdyStringPiece(d4.data(), d4.data_len()));
+
+  // Confirm moves an rvalue reference. Note that the test string "baz" is too
+  // short to trigger the move optimization, and instead a copy occurs.
+  SpdyString baz = "the quick brown fox";
+  SpdyDataIR d5(/* stream_id = */ 5, std::move(baz));
+  EXPECT_EQ("", baz);
+  EXPECT_EQ(SpdyStringPiece(d5.data(), d5.data_len()), "the quick brown fox");
+
+  // Confirms makes a copy of string literal.
+  SpdyDataIR d7(/* stream_id = */ 7, "something else");
+  EXPECT_EQ(SpdyStringPiece(d7.data(), d7.data_len()), "something else");
+
+  SpdyDataIR d8(/* stream_id = */ 8, "shawarma");
+  d8.set_padding_len(20);
+  EXPECT_EQ(28, d8.flow_control_window_consumed());
+}
+
+}  // namespace test
+}  // namespace spdy
diff --git a/spdy/core/spdy_protocol_test_utils.cc b/spdy/core/spdy_protocol_test_utils.cc
new file mode 100644
index 0000000..14d3385
--- /dev/null
+++ b/spdy/core/spdy_protocol_test_utils.cc
@@ -0,0 +1,155 @@
+// Copyright 2016 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "net/third_party/quiche/src/spdy/core/spdy_protocol_test_utils.h"
+
+#include <cstdint>
+
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string_piece.h"
+
+namespace spdy {
+namespace test {
+
+// TODO(jamessynge): Where it makes sense in these functions, it would be nice
+// to make use of the existing gMock matchers here, instead of rolling our own.
+
+::testing::AssertionResult VerifySpdyFrameWithHeaderBlockIREquals(
+    const SpdyFrameWithHeaderBlockIR& expected,
+    const SpdyFrameWithHeaderBlockIR& actual) {
+  VLOG(1) << "VerifySpdyFrameWithHeaderBlockIREquals";
+  VERIFY_TRUE(actual.header_block() == expected.header_block());
+  return ::testing::AssertionSuccess();
+}
+
+::testing::AssertionResult VerifySpdyFrameIREquals(const SpdyAltSvcIR& expected,
+                                                   const SpdyAltSvcIR& actual) {
+  VERIFY_EQ(expected.stream_id(), actual.stream_id());
+  VERIFY_EQ(expected.origin(), actual.origin());
+  VERIFY_THAT(actual.altsvc_vector(),
+              ::testing::ContainerEq(expected.altsvc_vector()));
+  return ::testing::AssertionSuccess();
+}
+
+::testing::AssertionResult VerifySpdyFrameIREquals(
+    const SpdyContinuationIR& expected,
+    const SpdyContinuationIR& actual) {
+  return ::testing::AssertionFailure()
+         << "VerifySpdyFrameIREquals SpdyContinuationIR not yet implemented";
+}
+
+::testing::AssertionResult VerifySpdyFrameIREquals(const SpdyDataIR& expected,
+                                                   const SpdyDataIR& actual) {
+  VLOG(1) << "VerifySpdyFrameIREquals SpdyDataIR";
+  VERIFY_EQ(expected.stream_id(), actual.stream_id());
+  VERIFY_EQ(expected.fin(), actual.fin());
+  VERIFY_EQ(expected.data_len(), actual.data_len());
+  if (expected.data() == nullptr) {
+    VERIFY_EQ(nullptr, actual.data());
+  } else {
+    VERIFY_EQ(SpdyStringPiece(expected.data(), expected.data_len()),
+              SpdyStringPiece(actual.data(), actual.data_len()));
+  }
+  VERIFY_SUCCESS(VerifySpdyFrameWithPaddingIREquals(expected, actual));
+  return ::testing::AssertionSuccess();
+}
+
+::testing::AssertionResult VerifySpdyFrameIREquals(const SpdyGoAwayIR& expected,
+                                                   const SpdyGoAwayIR& actual) {
+  VLOG(1) << "VerifySpdyFrameIREquals SpdyGoAwayIR";
+  VERIFY_EQ(expected.last_good_stream_id(), actual.last_good_stream_id());
+  VERIFY_EQ(expected.error_code(), actual.error_code());
+  VERIFY_EQ(expected.description(), actual.description());
+  return ::testing::AssertionSuccess();
+}
+
+::testing::AssertionResult VerifySpdyFrameIREquals(
+    const SpdyHeadersIR& expected,
+    const SpdyHeadersIR& actual) {
+  VLOG(1) << "VerifySpdyFrameIREquals SpdyHeadersIR";
+  VERIFY_EQ(expected.stream_id(), actual.stream_id());
+  VERIFY_EQ(expected.fin(), actual.fin());
+  VERIFY_SUCCESS(VerifySpdyFrameWithHeaderBlockIREquals(expected, actual));
+  VERIFY_EQ(expected.has_priority(), actual.has_priority());
+  if (expected.has_priority()) {
+    VERIFY_SUCCESS(VerifySpdyFrameWithPriorityIREquals(expected, actual));
+  }
+  VERIFY_SUCCESS(VerifySpdyFrameWithPaddingIREquals(expected, actual));
+  return ::testing::AssertionSuccess();
+}
+
+::testing::AssertionResult VerifySpdyFrameIREquals(const SpdyPingIR& expected,
+                                                   const SpdyPingIR& actual) {
+  VLOG(1) << "VerifySpdyFrameIREquals SpdyPingIR";
+  VERIFY_EQ(expected.id(), actual.id());
+  VERIFY_EQ(expected.is_ack(), actual.is_ack());
+  return ::testing::AssertionSuccess();
+}
+
+::testing::AssertionResult VerifySpdyFrameIREquals(
+    const SpdyPriorityIR& expected,
+    const SpdyPriorityIR& actual) {
+  VLOG(1) << "VerifySpdyFrameIREquals SpdyPriorityIR";
+  VERIFY_EQ(expected.stream_id(), actual.stream_id());
+  VERIFY_SUCCESS(VerifySpdyFrameWithPriorityIREquals(expected, actual));
+  return ::testing::AssertionSuccess();
+}
+
+::testing::AssertionResult VerifySpdyFrameIREquals(
+    const SpdyPushPromiseIR& expected,
+    const SpdyPushPromiseIR& actual) {
+  VLOG(1) << "VerifySpdyFrameIREquals SpdyPushPromiseIR";
+  VERIFY_EQ(expected.stream_id(), actual.stream_id());
+  VERIFY_SUCCESS(VerifySpdyFrameWithPaddingIREquals(expected, actual));
+  VERIFY_EQ(expected.promised_stream_id(), actual.promised_stream_id());
+  VERIFY_SUCCESS(VerifySpdyFrameWithHeaderBlockIREquals(expected, actual));
+  return ::testing::AssertionSuccess();
+}
+
+::testing::AssertionResult VerifySpdyFrameIREquals(
+    const SpdyRstStreamIR& expected,
+    const SpdyRstStreamIR& actual) {
+  VLOG(1) << "VerifySpdyFrameIREquals SpdyRstStreamIR";
+  VERIFY_EQ(expected.stream_id(), actual.stream_id());
+  VERIFY_EQ(expected.error_code(), actual.error_code());
+  return ::testing::AssertionSuccess();
+}
+
+::testing::AssertionResult VerifySpdyFrameIREquals(
+    const SpdySettingsIR& expected,
+    const SpdySettingsIR& actual) {
+  VLOG(1) << "VerifySpdyFrameIREquals SpdySettingsIR";
+  // Note, ignoring non-HTTP/2 fields such as clear_settings.
+  VERIFY_EQ(expected.is_ack(), actual.is_ack());
+
+  // Note, the following doesn't work because there isn't a comparator and
+  // formatter for SpdySettingsIR::Value. Fixable if we cared.
+  //
+  //   VERIFY_THAT(actual.values(), ::testing::ContainerEq(actual.values()));
+
+  VERIFY_EQ(expected.values().size(), actual.values().size());
+  for (const auto& entry : expected.values()) {
+    const auto& param = entry.first;
+    auto actual_itr = actual.values().find(param);
+    VERIFY_TRUE(!(actual_itr == actual.values().end()))
+        << "actual doesn't contain param: " << param;
+    uint32_t expected_value = entry.second;
+    uint32_t actual_value = actual_itr->second;
+    VERIFY_EQ(expected_value, actual_value)
+        << "Values don't match for parameter: " << param;
+  }
+
+  return ::testing::AssertionSuccess();
+}
+
+::testing::AssertionResult VerifySpdyFrameIREquals(
+    const SpdyWindowUpdateIR& expected,
+    const SpdyWindowUpdateIR& actual) {
+  VLOG(1) << "VerifySpdyFrameIREquals SpdyWindowUpdateIR";
+  VERIFY_EQ(expected.stream_id(), actual.stream_id());
+  VERIFY_EQ(expected.delta(), actual.delta());
+  return ::testing::AssertionSuccess();
+}
+
+}  // namespace test
+}  // namespace spdy
diff --git a/spdy/core/spdy_protocol_test_utils.h b/spdy/core/spdy_protocol_test_utils.h
new file mode 100644
index 0000000..2a16cb1
--- /dev/null
+++ b/spdy/core/spdy_protocol_test_utils.h
@@ -0,0 +1,149 @@
+// Copyright 2016 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef QUICHE_SPDY_CORE_SPDY_PROTOCOL_TEST_UTILS_H_
+#define QUICHE_SPDY_CORE_SPDY_PROTOCOL_TEST_UTILS_H_
+
+// These functions support tests that need to compare two concrete SpdyFrameIR
+// instances for equality. They return AssertionResult, so they may be used as
+// follows:
+//
+//    SomeSpdyFrameIRSubClass expected_ir(...);
+//    std::unique_ptr<SpdyFrameIR> collected_frame;
+//    ... some test code that may fill in collected_frame ...
+//    ASSERT_TRUE(VerifySpdyFrameIREquals(expected_ir, collected_frame.get()));
+//
+// TODO(jamessynge): Where it makes sense in these functions, it would be nice
+// to make use of the existing gMock matchers here, instead of rolling our own.
+
+#include <typeinfo>
+
+#include "base/logging.h"
+#include "testing/gmock/include/gmock/gmock.h"
+#include "testing/gtest/include/gtest/gtest.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_protocol.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_test_utils.h"
+
+namespace spdy {
+namespace test {
+
+// Verify the header entries in two SpdyFrameWithHeaderBlockIR instances
+// are the same.
+::testing::AssertionResult VerifySpdyFrameWithHeaderBlockIREquals(
+    const SpdyFrameWithHeaderBlockIR& expected,
+    const SpdyFrameWithHeaderBlockIR& actual);
+
+// Verify that the padding in two frames of type T is the same.
+template <class T>
+::testing::AssertionResult VerifySpdyFrameWithPaddingIREquals(const T& expected,
+                                                              const T& actual) {
+  VLOG(1) << "VerifySpdyFrameWithPaddingIREquals";
+  VERIFY_EQ(expected.padded(), actual.padded());
+  if (expected.padded()) {
+    VERIFY_EQ(expected.padding_payload_len(), actual.padding_payload_len());
+  }
+
+  return ::testing::AssertionSuccess();
+}
+
+// Verify the priority fields in two frames of type T are the same.
+template <class T>
+::testing::AssertionResult VerifySpdyFrameWithPriorityIREquals(
+    const T& expected,
+    const T& actual) {
+  VLOG(1) << "VerifySpdyFrameWithPriorityIREquals";
+  VERIFY_EQ(expected.parent_stream_id(), actual.parent_stream_id());
+  VERIFY_EQ(expected.weight(), actual.weight());
+  VERIFY_EQ(expected.exclusive(), actual.exclusive());
+  return ::testing::AssertionSuccess();
+}
+
+// Verify that two SpdyAltSvcIR frames are the same.
+::testing::AssertionResult VerifySpdyFrameIREquals(const SpdyAltSvcIR& expected,
+                                                   const SpdyAltSvcIR& actual);
+
+// VerifySpdyFrameIREquals for SpdyContinuationIR frames isn't really needed
+// because we don't really make use of SpdyContinuationIR, instead creating
+// SpdyHeadersIR or SpdyPushPromiseIR with the pre-encoding form of the HPACK
+// block (i.e. we don't yet have a CONTINUATION frame).
+//
+// ::testing::AssertionResult VerifySpdyFrameIREquals(
+//     const SpdyContinuationIR& expected,
+//     const SpdyContinuationIR& actual) {
+//   return ::testing::AssertionFailure()
+//          << "VerifySpdyFrameIREquals SpdyContinuationIR NYI";
+// }
+
+// Verify that two SpdyDataIR frames are the same.
+::testing::AssertionResult VerifySpdyFrameIREquals(const SpdyDataIR& expected,
+                                                   const SpdyDataIR& actual);
+
+// Verify that two SpdyGoAwayIR frames are the same.
+::testing::AssertionResult VerifySpdyFrameIREquals(const SpdyGoAwayIR& expected,
+                                                   const SpdyGoAwayIR& actual);
+
+// Verify that two SpdyHeadersIR frames are the same.
+::testing::AssertionResult VerifySpdyFrameIREquals(
+    const SpdyHeadersIR& expected,
+    const SpdyHeadersIR& actual);
+
+// Verify that two SpdyPingIR frames are the same.
+::testing::AssertionResult VerifySpdyFrameIREquals(const SpdyPingIR& expected,
+                                                   const SpdyPingIR& actual);
+
+// Verify that two SpdyPriorityIR frames are the same.
+::testing::AssertionResult VerifySpdyFrameIREquals(
+    const SpdyPriorityIR& expected,
+    const SpdyPriorityIR& actual);
+
+// Verify that two SpdyPushPromiseIR frames are the same.
+::testing::AssertionResult VerifySpdyFrameIREquals(
+    const SpdyPushPromiseIR& expected,
+    const SpdyPushPromiseIR& actual);
+
+// Verify that two SpdyRstStreamIR frames are the same.
+::testing::AssertionResult VerifySpdyFrameIREquals(
+    const SpdyRstStreamIR& expected,
+    const SpdyRstStreamIR& actual);
+
+// Verify that two SpdySettingsIR frames are the same.
+::testing::AssertionResult VerifySpdyFrameIREquals(
+    const SpdySettingsIR& expected,
+    const SpdySettingsIR& actual);
+
+// Verify that two SpdyWindowUpdateIR frames are the same.
+::testing::AssertionResult VerifySpdyFrameIREquals(
+    const SpdyWindowUpdateIR& expected,
+    const SpdyWindowUpdateIR& actual);
+
+// Verify that either expected and actual are both nullptr, or that both are not
+// nullptr, and that actual is of type E, and that it matches expected.
+template <class E>
+::testing::AssertionResult VerifySpdyFrameIREquals(const E* expected,
+                                                   const SpdyFrameIR* actual) {
+  if (expected == nullptr || actual == nullptr) {
+    VLOG(1) << "VerifySpdyFrameIREquals one null";
+    VERIFY_EQ(expected, nullptr);
+    VERIFY_EQ(actual, nullptr);
+    return ::testing::AssertionSuccess();
+  }
+  VLOG(1) << "VerifySpdyFrameIREquals not null";
+  VERIFY_EQ(actual->frame_type(), expected->frame_type());
+  const E* actual2 = down_cast<const E*>(actual);
+  return VerifySpdyFrameIREquals(*expected, *actual2);
+}
+
+// Verify that actual is not nullptr, that it is of type E and that it
+// matches expected.
+template <class E>
+::testing::AssertionResult VerifySpdyFrameIREquals(const E& expected,
+                                                   const SpdyFrameIR* actual) {
+  VLOG(1) << "VerifySpdyFrameIREquals";
+  return VerifySpdyFrameIREquals(&expected, actual);
+}
+
+}  // namespace test
+}  // namespace spdy
+
+#endif  // QUICHE_SPDY_CORE_SPDY_PROTOCOL_TEST_UTILS_H_
diff --git a/spdy/core/spdy_test_utils.cc b/spdy/core/spdy_test_utils.cc
new file mode 100644
index 0000000..dd6c417
--- /dev/null
+++ b/spdy/core/spdy_test_utils.cc
@@ -0,0 +1,119 @@
+// Copyright (c) 2012 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "net/third_party/quiche/src/spdy/core/spdy_test_utils.h"
+
+#include <algorithm>
+#include <cstring>
+#include <memory>
+#include <new>
+#include <utility>
+#include <vector>
+
+#include "base/logging.h"
+#include "testing/gtest/include/gtest/gtest.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_endianness_util.h"
+
+namespace spdy {
+namespace test {
+
+SpdyString HexDumpWithMarks(const unsigned char* data,
+                            int length,
+                            const bool* marks,
+                            int mark_length) {
+  static const char kHexChars[] = "0123456789abcdef";
+  static const int kColumns = 4;
+
+  const int kSizeLimit = 1024;
+  if (length > kSizeLimit || mark_length > kSizeLimit) {
+    LOG(ERROR) << "Only dumping first " << kSizeLimit << " bytes.";
+    length = std::min(length, kSizeLimit);
+    mark_length = std::min(mark_length, kSizeLimit);
+  }
+
+  SpdyString hex;
+  for (const unsigned char* row = data; length > 0;
+       row += kColumns, length -= kColumns) {
+    for (const unsigned char* p = row; p < row + 4; ++p) {
+      if (p < row + length) {
+        const bool mark =
+            (marks && (p - data) < mark_length && marks[p - data]);
+        hex += mark ? '*' : ' ';
+        hex += kHexChars[(*p & 0xf0) >> 4];
+        hex += kHexChars[*p & 0x0f];
+        hex += mark ? '*' : ' ';
+      } else {
+        hex += "    ";
+      }
+    }
+    hex = hex + "  ";
+
+    for (const unsigned char* p = row; p < row + 4 && p < row + length; ++p) {
+      hex += (*p >= 0x20 && *p <= 0x7f) ? (*p) : '.';
+    }
+
+    hex = hex + '\n';
+  }
+  return hex;
+}
+
+void CompareCharArraysWithHexError(const SpdyString& description,
+                                   const unsigned char* actual,
+                                   const int actual_len,
+                                   const unsigned char* expected,
+                                   const int expected_len) {
+  const int min_len = std::min(actual_len, expected_len);
+  const int max_len = std::max(actual_len, expected_len);
+  std::unique_ptr<bool[]> marks(new bool[max_len]);
+  bool identical = (actual_len == expected_len);
+  for (int i = 0; i < min_len; ++i) {
+    if (actual[i] != expected[i]) {
+      marks[i] = true;
+      identical = false;
+    } else {
+      marks[i] = false;
+    }
+  }
+  for (int i = min_len; i < max_len; ++i) {
+    marks[i] = true;
+  }
+  if (identical)
+    return;
+  ADD_FAILURE() << "Description:\n"
+                << description << "\n\nExpected:\n"
+                << HexDumpWithMarks(expected, expected_len, marks.get(),
+                                    max_len)
+                << "\nActual:\n"
+                << HexDumpWithMarks(actual, actual_len, marks.get(), max_len);
+}
+
+void SetFrameFlags(SpdySerializedFrame* frame, uint8_t flags) {
+  frame->data()[4] = flags;
+}
+
+void SetFrameLength(SpdySerializedFrame* frame, size_t length) {
+  CHECK_GT(1u << 14, length);
+  {
+    int32_t wire_length = SpdyHostToNet32(length);
+    memcpy(frame->data(), reinterpret_cast<char*>(&wire_length) + 1, 3);
+  }
+}
+
+void TestHeadersHandler::OnHeaderBlockStart() {
+  block_.clear();
+}
+
+void TestHeadersHandler::OnHeader(SpdyStringPiece name, SpdyStringPiece value) {
+  block_.AppendValueOrAddHeader(name, value);
+}
+
+void TestHeadersHandler::OnHeaderBlockEnd(
+    size_t header_bytes_parsed,
+    size_t compressed_header_bytes_parsed) {
+  header_bytes_parsed_ = header_bytes_parsed;
+  compressed_header_bytes_parsed_ = compressed_header_bytes_parsed;
+}
+
+}  // namespace test
+}  // namespace spdy
diff --git a/spdy/core/spdy_test_utils.h b/spdy/core/spdy_test_utils.h
new file mode 100644
index 0000000..bf62eeb
--- /dev/null
+++ b/spdy/core/spdy_test_utils.h
@@ -0,0 +1,74 @@
+// Copyright (c) 2012 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef QUICHE_SPDY_CORE_SPDY_TEST_UTILS_H_
+#define QUICHE_SPDY_CORE_SPDY_TEST_UTILS_H_
+
+#include <cstddef>
+#include <cstdint>
+
+#include "net/third_party/quiche/src/http2/platform/api/http2_test_helpers.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_header_block.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_headers_handler_interface.h"
+#include "net/third_party/quiche/src/spdy/core/spdy_protocol.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_bug_tracker.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string_piece.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_test_helpers.h"
+
+namespace spdy {
+
+inline bool operator==(SpdyStringPiece x,
+                       const SpdyHeaderBlock::ValueProxy& y) {
+  return x == y.as_string();
+}
+
+namespace test {
+
+SpdyString HexDumpWithMarks(const unsigned char* data,
+                            int length,
+                            const bool* marks,
+                            int mark_length);
+
+void CompareCharArraysWithHexError(const SpdyString& description,
+                                   const unsigned char* actual,
+                                   const int actual_len,
+                                   const unsigned char* expected,
+                                   const int expected_len);
+
+void SetFrameFlags(SpdySerializedFrame* frame, uint8_t flags);
+
+void SetFrameLength(SpdySerializedFrame* frame, size_t length);
+
+// A test implementation of SpdyHeadersHandlerInterface that correctly
+// reconstructs multiple header values for the same name.
+class TestHeadersHandler : public SpdyHeadersHandlerInterface {
+ public:
+  TestHeadersHandler() {}
+  TestHeadersHandler(const TestHeadersHandler&) = delete;
+  TestHeadersHandler& operator=(const TestHeadersHandler&) = delete;
+
+  void OnHeaderBlockStart() override;
+
+  void OnHeader(SpdyStringPiece name, SpdyStringPiece value) override;
+
+  void OnHeaderBlockEnd(size_t header_bytes_parsed,
+                        size_t compressed_header_bytes_parsed) override;
+
+  const SpdyHeaderBlock& decoded_block() const { return block_; }
+  size_t header_bytes_parsed() const { return header_bytes_parsed_; }
+  size_t compressed_header_bytes_parsed() const {
+    return compressed_header_bytes_parsed_;
+  }
+
+ private:
+  SpdyHeaderBlock block_;
+  size_t header_bytes_parsed_ = 0;
+  size_t compressed_header_bytes_parsed_ = 0;
+};
+
+}  // namespace test
+}  // namespace spdy
+
+#endif  // QUICHE_SPDY_CORE_SPDY_TEST_UTILS_H_
diff --git a/spdy/core/write_scheduler.h b/spdy/core/write_scheduler.h
new file mode 100644
index 0000000..07e5fb3
--- /dev/null
+++ b/spdy/core/write_scheduler.h
@@ -0,0 +1,156 @@
+// Copyright (c) 2016 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef QUICHE_SPDY_CORE_WRITE_SCHEDULER_H_
+#define QUICHE_SPDY_CORE_WRITE_SCHEDULER_H_
+
+#include <cstdint>
+#include <tuple>
+#include <vector>
+
+#include "net/third_party/quiche/src/spdy/core/spdy_protocol.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_export.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string.h"
+
+namespace spdy {
+
+// Abstract superclass for classes that decide which SPDY or HTTP/2 stream to
+// write next. Concrete subclasses implement various scheduling policies:
+//
+// PriorityWriteScheduler: implements SPDY priority-based stream scheduling,
+//     where (writable) higher-priority streams are always given precedence
+//     over lower-priority streams.
+//
+// Http2PriorityWriteScheduler: implements SPDY priority-based stream
+//     scheduling coupled with the HTTP/2 stream dependency model. This is only
+//     intended as a transitional step towards Http2WeightedWriteScheduler.
+//
+// Http2WeightedWriteScheduler (coming soon): implements the HTTP/2 stream
+//     dependency model with weighted stream scheduling, fully conforming to
+//     RFC 7540.
+//
+// The type used to represent stream IDs (StreamIdType) is templated in order
+// to allow for use by both SPDY and QUIC codebases. It must be a POD that
+// supports comparison (i.e., a numeric type).
+//
+// Each stream can be in one of two states: ready or not ready (for writing).
+// Ready state is changed by calling the MarkStreamReady() and
+// MarkStreamNotReady() methods. Only streams in the ready state can be
+// returned by PopNextReadyStream(); when returned by that method, the stream's
+// state changes to not ready.
+template <typename StreamIdType>
+class SPDY_EXPORT_PRIVATE WriteScheduler {
+ public:
+  typedef StreamPrecedence<StreamIdType> StreamPrecedenceType;
+
+  virtual ~WriteScheduler() {}
+
+  // Registers new stream |stream_id| with the scheduler, assigning it the
+  // given precedence. If the scheduler supports stream dependencies, the
+  // stream is inserted into the dependency tree under
+  // |precedence.parent_id()|.
+  //
+  // Preconditions: |stream_id| should be unregistered, and
+  // |precedence.parent_id()| should be registered or |kHttp2RootStreamId|.
+  virtual void RegisterStream(StreamIdType stream_id,
+                              const StreamPrecedenceType& precedence) = 0;
+
+  // Unregisters the given stream from the scheduler, which will no longer keep
+  // state for it.
+  //
+  // Preconditions: |stream_id| should be registered.
+  virtual void UnregisterStream(StreamIdType stream_id) = 0;
+
+  // Returns true if the given stream is currently registered.
+  virtual bool StreamRegistered(StreamIdType stream_id) const = 0;
+
+  // Returns the precedence of the specified stream. If the scheduler supports
+  // stream dependencies, calling |parent_id()| on the return value returns the
+  // stream's parent, and calling |exclusive()| returns true iff the specified
+  // stream is an only child of the parent stream.
+  //
+  // Preconditions: |stream_id| should be registered.
+  virtual StreamPrecedenceType GetStreamPrecedence(
+      StreamIdType stream_id) const = 0;
+
+  // Updates the precedence of the given stream. If the scheduler supports
+  // stream dependencies, |stream_id|'s parent will be updated to be
+  // |precedence.parent_id()| if it is not already.
+  //
+  // Preconditions: |stream_id| should be unregistered, and
+  // |precedence.parent_id()| should be registered or |kHttp2RootStreamId|.
+  virtual void UpdateStreamPrecedence(
+      StreamIdType stream_id,
+      const StreamPrecedenceType& precedence) = 0;
+
+  // Returns child streams of the given stream, if any. If the scheduler
+  // doesn't support stream dependencies, returns an empty vector.
+  //
+  // Preconditions: |stream_id| should be registered.
+  virtual std::vector<StreamIdType> GetStreamChildren(
+      StreamIdType stream_id) const = 0;
+
+  // Records time (in microseconds) of a read/write event for the given
+  // stream.
+  //
+  // Preconditions: |stream_id| should be registered.
+  virtual void RecordStreamEventTime(StreamIdType stream_id,
+                                     int64_t now_in_usec) = 0;
+
+  // Returns time (in microseconds) of the last read/write event for a stream
+  // with higher priority than the priority of the given stream, or 0 if there
+  // is no such event.
+  //
+  // Preconditions: |stream_id| should be registered.
+  virtual int64_t GetLatestEventWithPrecedence(
+      StreamIdType stream_id) const = 0;
+
+  // If the scheduler has any ready streams, returns the next scheduled
+  // ready stream, in the process transitioning the stream from ready to not
+  // ready.
+  //
+  // Preconditions: |HasReadyStreams() == true|
+  virtual StreamIdType PopNextReadyStream() = 0;
+
+  // If the scheduler has any ready streams, returns the next scheduled
+  // ready stream and its priority, in the process transitioning the stream from
+  // ready to not ready.
+  //
+  // Preconditions: |HasReadyStreams() == true|
+  virtual std::tuple<StreamIdType, StreamPrecedenceType>
+  PopNextReadyStreamAndPrecedence() = 0;
+
+  // Returns true if there's another stream ahead of the given stream in the
+  // scheduling queue.  This function can be called to see if the given stream
+  // should yield work to another stream.
+  //
+  // Preconditions: |stream_id| should be registered.
+  virtual bool ShouldYield(StreamIdType stream_id) const = 0;
+
+  // Marks the stream as ready to write. If the stream was already ready, does
+  // nothing. If add_to_front is true, the stream is scheduled ahead of other
+  // streams of the same priority/weight, otherwise it is scheduled behind them.
+  //
+  // Preconditions: |stream_id| should be registered.
+  virtual void MarkStreamReady(StreamIdType stream_id, bool add_to_front) = 0;
+
+  // Marks the stream as not ready to write. If the stream is not registered or
+  // not ready, does nothing.
+  //
+  // Preconditions: |stream_id| should be registered.
+  virtual void MarkStreamNotReady(StreamIdType stream_id) = 0;
+
+  // Returns true iff the scheduler has any ready streams.
+  virtual bool HasReadyStreams() const = 0;
+
+  // Returns the number of streams currently marked ready.
+  virtual size_t NumReadyStreams() const = 0;
+
+  // Returns summary of internal state, for logging/debugging.
+  virtual SpdyString DebugString() const = 0;
+};
+
+}  // namespace spdy
+
+#endif  // QUICHE_SPDY_CORE_WRITE_SCHEDULER_H_
diff --git a/spdy/core/zero_copy_output_buffer.h b/spdy/core/zero_copy_output_buffer.h
new file mode 100644
index 0000000..3f35bab
--- /dev/null
+++ b/spdy/core/zero_copy_output_buffer.h
@@ -0,0 +1,30 @@
+// Copyright 2017 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef QUICHE_SPDY_CORE_ZERO_COPY_OUTPUT_BUFFER_H_
+#define QUICHE_SPDY_CORE_ZERO_COPY_OUTPUT_BUFFER_H_
+
+#include <cstdint>
+
+namespace spdy {
+
+class ZeroCopyOutputBuffer {
+ public:
+  virtual ~ZeroCopyOutputBuffer() {}
+
+  // Returns the next available segment of memory to write. Will always return
+  // the same segment until AdvanceWritePtr is called.
+  virtual void Next(char** data, int* size) = 0;
+
+  // After writing to a buffer returned from Next(), the caller should call
+  // this method to indicate how many bytes were written.
+  virtual void AdvanceWritePtr(int64_t count) = 0;
+
+  // Returns the available capacity of the buffer.
+  virtual uint64_t BytesFree() const = 0;
+};
+
+}  // namespace spdy
+
+#endif  // QUICHE_SPDY_CORE_ZERO_COPY_OUTPUT_BUFFER_H_
diff --git a/spdy/platform/api/spdy_arraysize.h b/spdy/platform/api/spdy_arraysize.h
new file mode 100644
index 0000000..356051e
--- /dev/null
+++ b/spdy/platform/api/spdy_arraysize.h
@@ -0,0 +1,12 @@
+// Copyright (c) 2018 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef QUICHE_SPDY_PLATFORM_API_SPDY_ARRAYSIZE_H_
+#define QUICHE_SPDY_PLATFORM_API_SPDY_ARRAYSIZE_H_
+
+#include "net/spdy/platform/impl/spdy_arraysize_impl.h"
+
+#define SPDY_ARRAYSIZE(x) SPDY_ARRAYSIZE_IMPL(x)
+
+#endif  // QUICHE_SPDY_PLATFORM_API_SPDY_ARRAYSIZE_H_
diff --git a/spdy/platform/api/spdy_bug_tracker.h b/spdy/platform/api/spdy_bug_tracker.h
new file mode 100644
index 0000000..d750a21
--- /dev/null
+++ b/spdy/platform/api/spdy_bug_tracker.h
@@ -0,0 +1,15 @@
+// Copyright (c) 2019 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef QUICHE_SPDY_PLATFORM_API_SPDY_BUG_TRACKER_H_
+#define QUICHE_SPDY_PLATFORM_API_SPDY_BUG_TRACKER_H_
+
+#include "net/spdy/platform/impl/spdy_bug_tracker_impl.h"
+
+#define SPDY_BUG SPDY_BUG_IMPL
+#define SPDY_BUG_IF(condition) SPDY_BUG_IF_IMPL(condition)
+#define FLAGS_spdy_always_log_bugs_for_tests \
+  FLAGS_spdy_always_log_bugs_for_tests_impl
+
+#endif  // QUICHE_SPDY_PLATFORM_API_SPDY_BUG_TRACKER_H_
diff --git a/spdy/platform/api/spdy_containers.h b/spdy/platform/api/spdy_containers.h
new file mode 100644
index 0000000..e4f4c49
--- /dev/null
+++ b/spdy/platform/api/spdy_containers.h
@@ -0,0 +1,42 @@
+// Copyright (c) 2018 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef QUICHE_SPDY_PLATFORM_API_SPDY_CONTAINERS_H_
+#define QUICHE_SPDY_PLATFORM_API_SPDY_CONTAINERS_H_
+
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string_piece.h"
+#include "net/spdy/platform/impl/spdy_containers_impl.h"
+
+namespace spdy {
+
+template <typename KeyType>
+using SpdyHash = SpdyHashImpl<KeyType>;
+
+// SpdyHashMap does not guarantee pointer stability.
+template <typename KeyType,
+          typename ValueType,
+          typename Hash = SpdyHash<KeyType>>
+using SpdyHashMap = SpdyHashMapImpl<KeyType, ValueType, Hash>;
+
+// SpdyHashSet does not guarantee pointer stability.
+template <typename ElementType, typename Hasher, typename Eq>
+using SpdyHashSet = SpdyHashSetImpl<ElementType, Hasher, Eq>;
+
+// A map which offers insertion-ordered iteration.
+template <typename Key, typename Value, typename Hash = SpdyHash<Key>>
+using SpdyLinkedHashMap = SpdyLinkedHashMapImpl<Key, Value, Hash>;
+
+// A vector optimized for small sizes. Provides the same APIs as a std::vector.
+template <typename T, size_t N, typename A = std::allocator<T>>
+using SpdyInlinedVector = SpdyInlinedVectorImpl<T, N, A>;
+
+using SpdyStringPieceHash = SpdyStringPieceHashImpl;
+
+inline size_t SpdyHashStringPair(SpdyStringPiece a, SpdyStringPiece b) {
+  return SpdyHashStringPairImpl(a, b);
+}
+
+}  // namespace spdy
+
+#endif  // QUICHE_SPDY_PLATFORM_API_SPDY_CONTAINERS_H_
diff --git a/spdy/platform/api/spdy_endianness_util.h b/spdy/platform/api/spdy_endianness_util.h
new file mode 100644
index 0000000..e4074d7
--- /dev/null
+++ b/spdy/platform/api/spdy_endianness_util.h
@@ -0,0 +1,44 @@
+// Copyright (c) 2018 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef QUICHE_SPDY_PLATFORM_API_SPDY_ENDIANNESS_UTIL_H_
+#define QUICHE_SPDY_PLATFORM_API_SPDY_ENDIANNESS_UTIL_H_
+
+#include <stdint.h>
+
+#include "net/spdy/platform/impl/spdy_endianness_util_impl.h"
+
+namespace spdy {
+
+// Converts the bytes in |x| from network to host order (endianness), and
+// returns the result.
+inline uint16_t SpdyNetToHost16(uint16_t x) {
+  return SpdyNetToHost16Impl(x);
+}
+
+inline uint32_t SpdyNetToHost32(uint32_t x) {
+  return SpdyNetToHost32Impl(x);
+}
+
+inline uint64_t SpdyNetToHost64(uint64_t x) {
+  return SpdyNetToHost64Impl(x);
+}
+
+// Converts the bytes in |x| from host to network order (endianness), and
+// returns the result.
+inline uint16_t SpdyHostToNet16(uint16_t x) {
+  return SpdyHostToNet16Impl(x);
+}
+
+inline uint32_t SpdyHostToNet32(uint32_t x) {
+  return SpdyHostToNet32Impl(x);
+}
+
+inline uint64_t SpdyHostToNet64(uint64_t x) {
+  return SpdyHostToNet64Impl(x);
+}
+
+}  // namespace spdy
+
+#endif  // QUICHE_SPDY_PLATFORM_API_SPDY_ENDIANNESS_UTIL_H_
diff --git a/spdy/platform/api/spdy_estimate_memory_usage.h b/spdy/platform/api/spdy_estimate_memory_usage.h
new file mode 100644
index 0000000..6aa53c3
--- /dev/null
+++ b/spdy/platform/api/spdy_estimate_memory_usage.h
@@ -0,0 +1,21 @@
+// Copyright 2017 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef QUICHE_SPDY_PLATFORM_API_SPDY_ESTIMATE_MEMORY_USAGE_H_
+#define QUICHE_SPDY_PLATFORM_API_SPDY_ESTIMATE_MEMORY_USAGE_H_
+
+#include <cstddef>
+
+#include "net/spdy/platform/impl/spdy_estimate_memory_usage_impl.h"
+
+namespace spdy {
+
+template <class T>
+size_t SpdyEstimateMemoryUsage(const T& object) {
+  return SpdyEstimateMemoryUsageImpl(object);
+}
+
+}  // namespace spdy
+
+#endif  // QUICHE_SPDY_PLATFORM_API_SPDY_ESTIMATE_MEMORY_USAGE_H_
diff --git a/spdy/platform/api/spdy_export.h b/spdy/platform/api/spdy_export.h
new file mode 100644
index 0000000..ba92f79
--- /dev/null
+++ b/spdy/platform/api/spdy_export.h
@@ -0,0 +1,10 @@
+// Copyright 2017 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef QUICHE_SPDY_PLATFORM_API_SPDY_EXPORT_H_
+#define QUICHE_SPDY_PLATFORM_API_SPDY_EXPORT_H_
+
+#include "net/spdy/platform/impl/spdy_export_impl.h"
+
+#endif  // QUICHE_SPDY_PLATFORM_API_SPDY_EXPORT_H_
diff --git a/spdy/platform/api/spdy_flags.h b/spdy/platform/api/spdy_flags.h
new file mode 100644
index 0000000..f3446d9
--- /dev/null
+++ b/spdy/platform/api/spdy_flags.h
@@ -0,0 +1,13 @@
+// Copyright 2018 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef QUICHE_SPDY_PLATFORM_API_SPDY_FLAGS_H_
+#define QUICHE_SPDY_PLATFORM_API_SPDY_FLAGS_H_
+
+#include "net/spdy/platform/impl/spdy_flags_impl.h"
+
+#define GetSpdyReloadableFlag(flag) GetSpdyReloadableFlagImpl(flag)
+#define GetSpdyRestartFlag(flag) GetSpdyRestartFlagImpl(flag)
+
+#endif  // QUICHE_SPDY_PLATFORM_API_SPDY_FLAGS_H_
diff --git a/spdy/platform/api/spdy_macros.h b/spdy/platform/api/spdy_macros.h
new file mode 100644
index 0000000..a75c957
--- /dev/null
+++ b/spdy/platform/api/spdy_macros.h
@@ -0,0 +1,15 @@
+// Copyright (c) 2019 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef QUICHE_SPDY_PLATFORM_API_SPDY_MACROS_H_
+#define QUICHE_SPDY_PLATFORM_API_SPDY_MACROS_H_
+
+#include "net/spdy/platform/impl/spdy_macros_impl.h"
+
+#define SPDY_MUST_USE_RESULT SPDY_MUST_USE_RESULT_IMPL
+#define SPDY_UNUSED SPDY_UNUSED_IMPL
+
+#define SPDY_DVLOG_IF SPDY_DVLOG_IF_IMPL
+
+#endif  // QUICHE_SPDY_PLATFORM_API_SPDY_MACROS_H_
diff --git a/spdy/platform/api/spdy_mem_slice.h b/spdy/platform/api/spdy_mem_slice.h
new file mode 100644
index 0000000..0d67c00
--- /dev/null
+++ b/spdy/platform/api/spdy_mem_slice.h
@@ -0,0 +1,54 @@
+// Copyright 2017 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef QUICHE_SPDY_PLATFORM_API_SPDY_MEM_SLICE_H_
+#define QUICHE_SPDY_PLATFORM_API_SPDY_MEM_SLICE_H_
+
+#include <utility>
+
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_export.h"
+#include "net/spdy/platform/impl/spdy_mem_slice_impl.h"
+
+namespace spdy {
+
+// SpdyMemSlice is an internally reference counted data buffer used as the
+// source buffers for write operations. SpdyMemSlice implicitly maintains a
+// reference count and will free the underlying data buffer when the reference
+// count reaches zero.
+class SPDY_EXPORT_PRIVATE SpdyMemSlice {
+ public:
+  // Constructs an empty SpdyMemSlice with no underlying data and 0 reference
+  // count.
+  SpdyMemSlice() = default;
+
+  // Constructs a SpdyMemSlice with reference count 1 to a newly allocated data
+  // buffer of |length| bytes.
+  explicit SpdyMemSlice(size_t length) : impl_(length) {}
+
+  // Constructs a SpdyMemSlice from |impl|. It takes the reference away from
+  // |impl|.
+  explicit SpdyMemSlice(SpdyMemSliceImpl impl) : impl_(std::move(impl)) {}
+
+  SpdyMemSlice(const SpdyMemSlice& other) = delete;
+  SpdyMemSlice& operator=(const SpdyMemSlice& other) = delete;
+
+  // Move constructors. |other| will not hold a reference to the data buffer
+  // after this call completes.
+  SpdyMemSlice(SpdyMemSlice&& other) = default;
+  SpdyMemSlice& operator=(SpdyMemSlice&& other) = default;
+
+  ~SpdyMemSlice() = default;
+
+  // Returns a char pointer to underlying data buffer.
+  const char* data() const { return impl_.data(); }
+  // Returns the length of underlying data buffer.
+  size_t length() const { return impl_.length(); }
+
+ private:
+  SpdyMemSliceImpl impl_;
+};
+
+}  // namespace spdy
+
+#endif  // QUICHE_SPDY_PLATFORM_API_SPDY_MEM_SLICE_H_
diff --git a/spdy/platform/api/spdy_mem_slice_test.cc b/spdy/platform/api/spdy_mem_slice_test.cc
new file mode 100644
index 0000000..af323f6
--- /dev/null
+++ b/spdy/platform/api/spdy_mem_slice_test.cc
@@ -0,0 +1,47 @@
+// Copyright 2017 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_mem_slice.h"
+
+#include <utility>
+
+#include "testing/gtest/include/gtest/gtest.h"
+
+namespace spdy {
+namespace test {
+namespace {
+
+class SpdyMemSliceTest : public ::testing::Test {
+ public:
+  SpdyMemSliceTest() {
+    slice_ = SpdyMemSlice(1024);
+    orig_data_ = slice_.data();
+    orig_length_ = slice_.length();
+  }
+
+  SpdyMemSlice slice_;
+  const char* orig_data_;
+  size_t orig_length_;
+};
+
+TEST_F(SpdyMemSliceTest, MoveConstruct) {
+  SpdyMemSlice moved(std::move(slice_));
+  EXPECT_EQ(moved.data(), orig_data_);
+  EXPECT_EQ(moved.length(), orig_length_);
+  EXPECT_EQ(nullptr, slice_.data());
+  EXPECT_EQ(0u, slice_.length());
+}
+
+TEST_F(SpdyMemSliceTest, MoveAssign) {
+  SpdyMemSlice moved;
+  moved = std::move(slice_);
+  EXPECT_EQ(moved.data(), orig_data_);
+  EXPECT_EQ(moved.length(), orig_length_);
+  EXPECT_EQ(nullptr, slice_.data());
+  EXPECT_EQ(0u, slice_.length());
+}
+
+}  // namespace
+}  // namespace test
+}  // namespace spdy
diff --git a/spdy/platform/api/spdy_ptr_util.h b/spdy/platform/api/spdy_ptr_util.h
new file mode 100644
index 0000000..32b8515
--- /dev/null
+++ b/spdy/platform/api/spdy_ptr_util.h
@@ -0,0 +1,27 @@
+// Copyright 2017 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef QUICHE_SPDY_PLATFORM_API_SPDY_PTR_UTIL_H_
+#define QUICHE_SPDY_PLATFORM_API_SPDY_PTR_UTIL_H_
+
+#include <memory>
+#include <utility>
+
+#include "net/spdy/platform/impl/spdy_ptr_util_impl.h"
+
+namespace spdy {
+
+template <typename T, typename... Args>
+std::unique_ptr<T> SpdyMakeUnique(Args&&... args) {
+  return SpdyMakeUniqueImpl<T>(std::forward<Args>(args)...);
+}
+
+template <typename T>
+std::unique_ptr<T> SpdyWrapUnique(T* ptr) {
+  return SpdyWrapUniqueImpl<T>(ptr);
+}
+
+}  // namespace spdy
+
+#endif  // QUICHE_SPDY_PLATFORM_API_SPDY_PTR_UTIL_H_
diff --git a/spdy/platform/api/spdy_string.h b/spdy/platform/api/spdy_string.h
new file mode 100644
index 0000000..16eb9e5
--- /dev/null
+++ b/spdy/platform/api/spdy_string.h
@@ -0,0 +1,16 @@
+// Copyright (c) 2017 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef QUICHE_SPDY_PLATFORM_API_SPDY_STRING_H_
+#define QUICHE_SPDY_PLATFORM_API_SPDY_STRING_H_
+
+#include "net/spdy/platform/impl/spdy_string_impl.h"
+
+namespace spdy {
+
+using SpdyString = SpdyStringImpl;
+
+}  // namespace spdy
+
+#endif  // QUICHE_SPDY_PLATFORM_API_SPDY_STRING_H_
diff --git a/spdy/platform/api/spdy_string_piece.h b/spdy/platform/api/spdy_string_piece.h
new file mode 100644
index 0000000..37eea70
--- /dev/null
+++ b/spdy/platform/api/spdy_string_piece.h
@@ -0,0 +1,16 @@
+// Copyright (c) 2017 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef QUICHE_SPDY_PLATFORM_API_SPDY_STRING_PIECE_H_
+#define QUICHE_SPDY_PLATFORM_API_SPDY_STRING_PIECE_H_
+
+#include "net/spdy/platform/impl/spdy_string_piece_impl.h"
+
+namespace spdy {
+
+using SpdyStringPiece = SpdyStringPieceImpl;
+
+}  // namespace spdy
+
+#endif  // QUICHE_SPDY_PLATFORM_API_SPDY_STRING_PIECE_H_
diff --git a/spdy/platform/api/spdy_string_utils.h b/spdy/platform/api/spdy_string_utils.h
new file mode 100644
index 0000000..7554f79
--- /dev/null
+++ b/spdy/platform/api/spdy_string_utils.h
@@ -0,0 +1,58 @@
+// Copyright 2017 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef QUICHE_SPDY_PLATFORM_API_SPDY_STRING_UTILS_H_
+#define QUICHE_SPDY_PLATFORM_API_SPDY_STRING_UTILS_H_
+
+#include <utility>
+
+// The following header file has to be included from at least
+// non-test file in order to avoid strange linking errors.
+// TODO(bnc): Remove this include as soon as it is included elsewhere in
+// non-test code.
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_mem_slice.h"
+
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string_piece.h"
+#include "net/spdy/platform/impl/spdy_string_utils_impl.h"
+
+namespace spdy {
+
+template <typename... Args>
+inline SpdyString SpdyStrCat(const Args&... args) {
+  return SpdyStrCatImpl(std::forward<const Args&>(args)...);
+}
+
+template <typename... Args>
+inline void SpdyStrAppend(SpdyString* output, const Args&... args) {
+  SpdyStrAppendImpl(output, std::forward<const Args&>(args)...);
+}
+
+inline char SpdyHexDigitToInt(char c) {
+  return SpdyHexDigitToIntImpl(c);
+}
+
+inline SpdyString SpdyHexDecode(SpdyStringPiece data) {
+  return SpdyHexDecodeImpl(data);
+}
+
+inline bool SpdyHexDecodeToUInt32(SpdyStringPiece data, uint32_t* out) {
+  return SpdyHexDecodeToUInt32Impl(data, out);
+}
+
+inline SpdyString SpdyHexEncode(const char* bytes, size_t size) {
+  return SpdyHexEncodeImpl(bytes, size);
+}
+
+inline SpdyString SpdyHexEncodeUInt32AndTrim(uint32_t data) {
+  return SpdyHexEncodeUInt32AndTrimImpl(data);
+}
+
+inline SpdyString SpdyHexDump(SpdyStringPiece data) {
+  return SpdyHexDumpImpl(data);
+}
+
+}  // namespace spdy
+
+#endif  // QUICHE_SPDY_PLATFORM_API_SPDY_STRING_UTILS_H_
diff --git a/spdy/platform/api/spdy_string_utils_test.cc b/spdy/platform/api/spdy_string_utils_test.cc
new file mode 100644
index 0000000..3f7e6a1
--- /dev/null
+++ b/spdy/platform/api/spdy_string_utils_test.cc
@@ -0,0 +1,242 @@
+// Copyright 2017 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string_utils.h"
+
+#include <cstdint>
+
+#include "testing/gtest/include/gtest/gtest.h"
+#include "net/third_party/quiche/src/spdy/platform/api/spdy_string_piece.h"
+
+namespace spdy {
+namespace test {
+namespace {
+
+TEST(SpdyStringUtilsTest, SpdyStrCat) {
+  // No arguments.
+  EXPECT_EQ("", SpdyStrCat());
+
+  // Single string-like argument.
+  const char kFoo[] = "foo";
+  const SpdyString string_foo(kFoo);
+  const SpdyStringPiece stringpiece_foo(string_foo);
+  EXPECT_EQ("foo", SpdyStrCat(kFoo));
+  EXPECT_EQ("foo", SpdyStrCat(string_foo));
+  EXPECT_EQ("foo", SpdyStrCat(stringpiece_foo));
+
+  // Two string-like arguments.
+  const char kBar[] = "bar";
+  const SpdyStringPiece stringpiece_bar(kBar);
+  const SpdyString string_bar(kBar);
+  EXPECT_EQ("foobar", SpdyStrCat(kFoo, kBar));
+  EXPECT_EQ("foobar", SpdyStrCat(kFoo, string_bar));
+  EXPECT_EQ("foobar", SpdyStrCat(kFoo, stringpiece_bar));
+  EXPECT_EQ("foobar", SpdyStrCat(string_foo, kBar));
+  EXPECT_EQ("foobar", SpdyStrCat(string_foo, string_bar));
+  EXPECT_EQ("foobar", SpdyStrCat(string_foo, stringpiece_bar));
+  EXPECT_EQ("foobar", SpdyStrCat(stringpiece_foo, kBar));
+  EXPECT_EQ("foobar", SpdyStrCat(stringpiece_foo, string_bar));
+  EXPECT_EQ("foobar", SpdyStrCat(stringpiece_foo, stringpiece_bar));
+
+  // Many-many arguments.
+  EXPECT_EQ(
+      "foobarbazquxquuxquuzcorgegraultgarplywaldofredplughxyzzythud",
+      SpdyStrCat("foo", "bar", "baz", "qux", "quux", "quuz", "corge", "grault",
+                 "garply", "waldo", "fred", "plugh", "xyzzy", "thud"));
+
+  // Numerical arguments.
+  const int16_t i = 1;
+  const uint64_t u = 8;
+  const double d = 3.1415;
+
+  EXPECT_EQ("1 8", SpdyStrCat(i, " ", u));
+  EXPECT_EQ("3.14151181", SpdyStrCat(d, i, i, u, i));
+  EXPECT_EQ("i: 1, u: 8, d: 3.1415",
+            SpdyStrCat("i: ", i, ", u: ", u, ", d: ", d));
+
+  // Boolean arguments.
+  const bool t = true;
+  const bool f = false;
+
+  EXPECT_EQ("1", SpdyStrCat(t));
+  EXPECT_EQ("0", SpdyStrCat(f));
+  EXPECT_EQ("0110", SpdyStrCat(f, t, t, f));
+
+  // Mixed string-like, numerical, and Boolean arguments.
+  EXPECT_EQ("foo1foo081bar3.14151",
+            SpdyStrCat(kFoo, i, string_foo, f, u, t, stringpiece_bar, d, t));
+  EXPECT_EQ("3.141511bar18bar13.14150",
+            SpdyStrCat(d, t, t, string_bar, i, u, kBar, t, d, f));
+}
+
+TEST(SpdyStringUtilsTest, SpdyStrAppend) {
+  // No arguments on empty string.
+  SpdyString output;
+  SpdyStrAppend(&output);
+  EXPECT_TRUE(output.empty());
+
+  // Single string-like argument.
+  const char kFoo[] = "foo";
+  const SpdyString string_foo(kFoo);
+  const SpdyStringPiece stringpiece_foo(string_foo);
+  SpdyStrAppend(&output, kFoo);
+  EXPECT_EQ("foo", output);
+  SpdyStrAppend(&output, string_foo);
+  EXPECT_EQ("foofoo", output);
+  SpdyStrAppend(&output, stringpiece_foo);
+  EXPECT_EQ("foofoofoo", output);
+
+  // No arguments on non-empty string.
+  SpdyStrAppend(&output);
+  EXPECT_EQ("foofoofoo", output);
+
+  output.clear();
+
+  // Two string-like arguments.
+  const char kBar[] = "bar";
+  const SpdyStringPiece stringpiece_bar(kBar);
+  const SpdyString string_bar(kBar);
+  SpdyStrAppend(&output, kFoo, kBar);
+  EXPECT_EQ("foobar", output);
+  SpdyStrAppend(&output, kFoo, string_bar);
+  EXPECT_EQ("foobarfoobar", output);
+  SpdyStrAppend(&output, kFoo, stringpiece_bar);
+  EXPECT_EQ("foobarfoobarfoobar", output);
+  SpdyStrAppend(&output, string_foo, kBar);
+  EXPECT_EQ("foobarfoobarfoobarfoobar", output);
+
+  output.clear();
+
+  SpdyStrAppend(&output, string_foo, string_bar);
+  EXPECT_EQ("foobar", output);
+  SpdyStrAppend(&output, string_foo, stringpiece_bar);
+  EXPECT_EQ("foobarfoobar", output);
+  SpdyStrAppend(&output, stringpiece_foo, kBar);
+  EXPECT_EQ("foobarfoobarfoobar", output);
+  SpdyStrAppend(&output, stringpiece_foo, string_bar);
+  EXPECT_EQ("foobarfoobarfoobarfoobar", output);
+
+  output.clear();
+
+  SpdyStrAppend(&output, stringpiece_foo, stringpiece_bar);
+  EXPECT_EQ("foobar", output);
+
+  // Many-many arguments.
+  SpdyStrAppend(&output, "foo", "bar", "baz", "qux", "quux", "quuz", "corge",
+                "grault", "garply", "waldo", "fred", "plugh", "xyzzy", "thud");
+  EXPECT_EQ(
+      "foobarfoobarbazquxquuxquuzcorgegraultgarplywaldofredplughxyzzythud",
+      output);
+
+  output.clear();
+
+  // Numerical arguments.
+  const int16_t i = 1;
+  const uint64_t u = 8;
+  const double d = 3.1415;
+
+  SpdyStrAppend(&output, i, " ", u);
+  EXPECT_EQ("1 8", output);
+  SpdyStrAppend(&output, d, i, i, u, i);
+  EXPECT_EQ("1 83.14151181", output);
+  SpdyStrAppend(&output, "i: ", i, ", u: ", u, ", d: ", d);
+  EXPECT_EQ("1 83.14151181i: 1, u: 8, d: 3.1415", output);
+
+  output.clear();
+
+  // Boolean arguments.
+  const bool t = true;
+  const bool f = false;
+
+  SpdyStrAppend(&output, t);
+  EXPECT_EQ("1", output);
+  SpdyStrAppend(&output, f);
+  EXPECT_EQ("10", output);
+  SpdyStrAppend(&output, f, t, t, f);
+  EXPECT_EQ("100110", output);
+
+  output.clear();
+
+  // Mixed string-like, numerical, and Boolean arguments.
+  SpdyStrAppend(&output, kFoo, i, string_foo, f, u, t, stringpiece_bar, d, t);
+  EXPECT_EQ("foo1foo081bar3.14151", output);
+  SpdyStrAppend(&output, d, t, t, string_bar, i, u, kBar, t, d, f);
+  EXPECT_EQ("foo1foo081bar3.141513.141511bar18bar13.14150", output);
+}
+
+TEST(SpdyStringUtilsTest, SpdyHexDigitToInt) {
+  EXPECT_EQ(0, SpdyHexDigitToInt('0'));
+  EXPECT_EQ(1, SpdyHexDigitToInt('1'));
+  EXPECT_EQ(2, SpdyHexDigitToInt('2'));
+  EXPECT_EQ(3, SpdyHexDigitToInt('3'));
+  EXPECT_EQ(4, SpdyHexDigitToInt('4'));
+  EXPECT_EQ(5, SpdyHexDigitToInt('5'));
+  EXPECT_EQ(6, SpdyHexDigitToInt('6'));
+  EXPECT_EQ(7, SpdyHexDigitToInt('7'));
+  EXPECT_EQ(8, SpdyHexDigitToInt('8'));
+  EXPECT_EQ(9, SpdyHexDigitToInt('9'));
+
+  EXPECT_EQ(10, SpdyHexDigitToInt('a'));
+  EXPECT_EQ(11, SpdyHexDigitToInt('b'));
+  EXPECT_EQ(12, SpdyHexDigitToInt('c'));
+  EXPECT_EQ(13, SpdyHexDigitToInt('d'));
+  EXPECT_EQ(14, SpdyHexDigitToInt('e'));
+  EXPECT_EQ(15, SpdyHexDigitToInt('f'));
+
+  EXPECT_EQ(10, SpdyHexDigitToInt('A'));
+  EXPECT_EQ(11, SpdyHexDigitToInt('B'));
+  EXPECT_EQ(12, SpdyHexDigitToInt('C'));
+  EXPECT_EQ(13, SpdyHexDigitToInt('D'));
+  EXPECT_EQ(14, SpdyHexDigitToInt('E'));
+  EXPECT_EQ(15, SpdyHexDigitToInt('F'));
+}
+
+TEST(SpdyStringUtilsTest, SpdyHexDecodeToUInt32) {
+  uint32_t out;
+  EXPECT_TRUE(SpdyHexDecodeToUInt32("0", &out));
+  EXPECT_EQ(0u, out);
+  EXPECT_TRUE(SpdyHexDecodeToUInt32("00", &out));
+  EXPECT_EQ(0u, out);
+  EXPECT_TRUE(SpdyHexDecodeToUInt32("0000000", &out));
+  EXPECT_EQ(0u, out);
+  EXPECT_TRUE(SpdyHexDecodeToUInt32("00000000", &out));
+  EXPECT_EQ(0u, out);
+  EXPECT_TRUE(SpdyHexDecodeToUInt32("1", &out));
+  EXPECT_EQ(1u, out);
+  EXPECT_TRUE(SpdyHexDecodeToUInt32("ffffFFF", &out));
+  EXPECT_EQ(0xFFFFFFFu, out);
+  EXPECT_TRUE(SpdyHexDecodeToUInt32("fFfFffFf", &out));
+  EXPECT_EQ(0xFFFFFFFFu, out);
+  EXPECT_TRUE(SpdyHexDecodeToUInt32("01AEF", &out));
+  EXPECT_EQ(0x1AEFu, out);
+  EXPECT_TRUE(SpdyHexDecodeToUInt32("abcde", &out));
+  EXPECT_EQ(0xABCDEu, out);
+
+  EXPECT_FALSE(SpdyHexDecodeToUInt32("", &out));
+  EXPECT_FALSE(SpdyHexDecodeToUInt32("111111111", &out));
+  EXPECT_FALSE(SpdyHexDecodeToUInt32("1111111111", &out));
+  EXPECT_FALSE(SpdyHexDecodeToUInt32("0x1111", &out));
+}
+
+TEST(SpdyStringUtilsTest, SpdyHexEncode) {
+  unsigned char bytes[] = {0x01, 0xff, 0x02, 0xfe, 0x03, 0x80, 0x81};
+  EXPECT_EQ("01ff02fe038081",
+            SpdyHexEncode(reinterpret_cast<char*>(bytes), sizeof(bytes)));
+}
+
+TEST(SpdyStringUtilsTest, SpdyHexEncodeUInt32AndTrim) {
+  EXPECT_EQ("0", SpdyHexEncodeUInt32AndTrim(0));
+  EXPECT_EQ("1", SpdyHexEncodeUInt32AndTrim(1));
+  EXPECT_EQ("a", SpdyHexEncodeUInt32AndTrim(0xA));
+  EXPECT_EQ("f", SpdyHexEncodeUInt32AndTrim(0xF));
+  EXPECT_EQ("a9", SpdyHexEncodeUInt32AndTrim(0xA9));
+  EXPECT_EQ("9abcdef", SpdyHexEncodeUInt32AndTrim(0x9ABCDEF));
+  EXPECT_EQ("12345678", SpdyHexEncodeUInt32AndTrim(0x12345678));
+  EXPECT_EQ("ffffffff", SpdyHexEncodeUInt32AndTrim(0xFFFFFFFF));
+  EXPECT_EQ("10000001", SpdyHexEncodeUInt32AndTrim(0x10000001));
+}
+
+}  // namespace
+}  // namespace test
+}  // namespace spdy
diff --git a/spdy/platform/api/spdy_test_helpers.h b/spdy/platform/api/spdy_test_helpers.h
new file mode 100644
index 0000000..367d330
--- /dev/null
+++ b/spdy/platform/api/spdy_test_helpers.h
@@ -0,0 +1,12 @@
+// Copyright (c) 2019 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef QUICHE_SPDY_PLATFORM_API_SPDY_TEST_HELPERS_H_
+#define QUICHE_SPDY_PLATFORM_API_SPDY_TEST_HELPERS_H_
+
+#include "net/spdy/platform/impl/spdy_test_helpers_impl.h"
+
+#define EXPECT_SPDY_BUG EXPECT_SPDY_BUG_IMPL
+
+#endif  // QUICHE_SPDY_PLATFORM_API_SPDY_TEST_HELPERS_H_
diff --git a/spdy/platform/api/spdy_test_utils_prod.h b/spdy/platform/api/spdy_test_utils_prod.h
new file mode 100644
index 0000000..1466770
--- /dev/null
+++ b/spdy/platform/api/spdy_test_utils_prod.h
@@ -0,0 +1,12 @@
+// Copyright (c) 2019 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef QUICHE_SPDY_PLATFORM_API_SPDY_TEST_UTILS_PROD_H_
+#define QUICHE_SPDY_PLATFORM_API_SPDY_TEST_UTILS_PROD_H_
+
+#include "net/spdy/platform/impl/spdy_test_utils_prod_impl.h"
+
+#define SPDY_FRIEND_TEST SPDY_FRIEND_TEST_IMPL
+
+#endif  // QUICHE_SPDY_PLATFORM_API_SPDY_TEST_UTILS_PROD_H_
diff --git a/spdy/platform/api/spdy_unsafe_arena.h b/spdy/platform/api/spdy_unsafe_arena.h
new file mode 100644
index 0000000..77185e1
--- /dev/null
+++ b/spdy/platform/api/spdy_unsafe_arena.h
@@ -0,0 +1,16 @@
+// Copyright (c) 2019 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef QUICHE_SPDY_PLATFORM_API_SPDY_UNSAFE_ARENA_H_
+#define QUICHE_SPDY_PLATFORM_API_SPDY_UNSAFE_ARENA_H_
+
+#include "net/spdy/platform/impl/spdy_unsafe_arena_impl.h"
+
+namespace spdy {
+
+using SpdyUnsafeArena = SpdyUnsafeArenaImpl;
+
+}  // namespace spdy
+
+#endif  // QUICHE_SPDY_PLATFORM_API_SPDY_UNSAFE_ARENA_H_
