Bug 1248197 - Remove spdy/3.1 support. r?mcmanus draft
authorNicholas Hurley <hurley@todesschaf.org>
Fri, 15 Jul 2016 15:13:49 -0700
changeset 392856 398e8d9d1f2215f281d40547a6342eb7555217ad
parent 392855 ff1ef8ec0fd800bf6856c1572c3b1610c45e9b6a
child 526425 426b66234e4cfdbd75c4ebb9332881bd93a0af6f
push id24137
push userbmo:hurley@todesschaf.org
push dateTue, 26 Jul 2016 12:12:18 +0000
reviewersmcmanus
bugs1248197
milestone50.0a1
Bug 1248197 - Remove spdy/3.1 support. r?mcmanus MozReview-Commit-ID: 1RgzxOY00Le
modules/libpref/init/all.js
netwerk/base/Dashboard.cpp
netwerk/protocol/http/ASpdySession.cpp
netwerk/protocol/http/ASpdySession.h
netwerk/protocol/http/AlternateServices.cpp
netwerk/protocol/http/ConnectionDiagnostics.cpp
netwerk/protocol/http/PSpdyPush.h
netwerk/protocol/http/SpdyPush31.cpp
netwerk/protocol/http/SpdyPush31.h
netwerk/protocol/http/SpdySession31.cpp
netwerk/protocol/http/SpdySession31.h
netwerk/protocol/http/SpdyStream31.cpp
netwerk/protocol/http/SpdyStream31.h
netwerk/protocol/http/SpdyZlibReporter.cpp
netwerk/protocol/http/SpdyZlibReporter.h
netwerk/protocol/http/moz.build
netwerk/protocol/http/nsHttp.cpp
netwerk/protocol/http/nsHttp.h
netwerk/protocol/http/nsHttpHandler.cpp
netwerk/protocol/http/nsHttpHandler.h
netwerk/test/unit/test_http2.js
netwerk/test/unit/test_spdy.js
netwerk/test/unit/xpcshell.ini
testing/xpcshell/moz-spdy/README.txt
testing/xpcshell/moz-spdy/moz-spdy.js
testing/xpcshell/moz-spdy/spdy-ca.pem
testing/xpcshell/moz-spdy/spdy-cert.pem
testing/xpcshell/moz-spdy/spdy-key.pem
testing/xpcshell/node-spdy/README.md
testing/xpcshell/node-spdy/keys/spdy-cert.pem
testing/xpcshell/node-spdy/keys/spdy-csr.pem
testing/xpcshell/node-spdy/keys/spdy-key.pem
testing/xpcshell/node-spdy/lib/spdy.js
testing/xpcshell/node-spdy/lib/spdy/client.js
testing/xpcshell/node-spdy/lib/spdy/connection.js
testing/xpcshell/node-spdy/lib/spdy/protocol/constants.js
testing/xpcshell/node-spdy/lib/spdy/protocol/dictionary.js
testing/xpcshell/node-spdy/lib/spdy/protocol/framer.js
testing/xpcshell/node-spdy/lib/spdy/protocol/index.js
testing/xpcshell/node-spdy/lib/spdy/protocol/parser.js
testing/xpcshell/node-spdy/lib/spdy/response.js
testing/xpcshell/node-spdy/lib/spdy/scheduler.js
testing/xpcshell/node-spdy/lib/spdy/server.js
testing/xpcshell/node-spdy/lib/spdy/stream.js
testing/xpcshell/node-spdy/lib/spdy/utils.js
testing/xpcshell/node-spdy/lib/spdy/zlib-pool.js
testing/xpcshell/node-spdy/package.json
testing/xpcshell/node-spdy/test/benchmarks/syn.js
testing/xpcshell/node-spdy/test/fixtures/frames.js
testing/xpcshell/node-spdy/test/fixtures/keys.js
testing/xpcshell/node-spdy/test/unit/connect-test.js
testing/xpcshell/node-spdy/test/unit/plain-test.js
testing/xpcshell/node-spdy/test/unit/proxy-test.js
testing/xpcshell/node-spdy/test/unit/stream-test.js
testing/xpcshell/runxpcshelltests.py
--- a/modules/libpref/init/all.js
+++ b/modules/libpref/init/all.js
@@ -1491,17 +1491,16 @@ pref("network.http.fast-fallback-to-IPv4
 #ifdef RELEASE_BUILD
 pref("network.http.bypass-cachelock-threshold", 200000);
 #else
 pref("network.http.bypass-cachelock-threshold", 250);
 #endif
 
 // Try and use SPDY when using SSL
 pref("network.http.spdy.enabled", true);
-pref("network.http.spdy.enabled.v3-1", false);
 pref("network.http.spdy.enabled.http2", true);
 pref("network.http.spdy.enabled.deps", true);
 pref("network.http.spdy.enforce-tls-profile", true);
 pref("network.http.spdy.chunk-size", 16000);
 pref("network.http.spdy.timeout", 180);
 pref("network.http.spdy.coalesce-hostnames", true);
 pref("network.http.spdy.persistent-settings", false);
 pref("network.http.spdy.ping-threshold", 58);
--- a/netwerk/base/Dashboard.cpp
+++ b/netwerk/base/Dashboard.cpp
@@ -772,22 +772,18 @@ HttpConnInfo::SetHTTP1ProtocolVersion(ui
     default:
         protocolVersion.AssignLiteral(u"unknown protocol version");
     }
 }
 
 void
 HttpConnInfo::SetHTTP2ProtocolVersion(uint8_t pv)
 {
-    if (pv == SPDY_VERSION_31) {
-        protocolVersion.AssignLiteral(u"spdy/3.1");
-    } else {
-        MOZ_ASSERT (pv == HTTP_VERSION_2);
-        protocolVersion.Assign(u"h2");
-    }
+    MOZ_ASSERT (pv == HTTP_VERSION_2);
+    protocolVersion.Assign(u"h2");
 }
 
 NS_IMETHODIMP
 Dashboard::RequestConnection(const nsACString& aHost, uint32_t aPort,
                              const char *aProtocol, uint32_t aTimeout,
                              NetDashboardCallback *aCallback)
 {
     nsresult rv;
--- a/netwerk/protocol/http/ASpdySession.cpp
+++ b/netwerk/protocol/http/ASpdySession.cpp
@@ -3,27 +3,25 @@
 /* This Source Code Form is subject to the terms of the Mozilla Public
  * License, v. 2.0. If a copy of the MPL was not distributed with this
  * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
 
 // HttpLog.h should generally be included first
 #include "HttpLog.h"
 
 /*
-  Currently supported are h2 and spdy/3.1
+  Currently supported is h2
 */
 
 #include "nsHttp.h"
 #include "nsHttpHandler.h"
 
 #include "ASpdySession.h"
 #include "PSpdyPush.h"
-#include "SpdyPush31.h"
 #include "Http2Push.h"
-#include "SpdySession31.h"
 #include "Http2Session.h"
 
 #include "mozilla/Telemetry.h"
 
 namespace mozilla {
 namespace net {
 
 ASpdySession::ASpdySession()
@@ -35,65 +33,44 @@ ASpdySession::~ASpdySession()
 }
 
 ASpdySession *
 ASpdySession::NewSpdySession(uint32_t version,
                              nsISocketTransport *aTransport)
 {
   // This is a necko only interface, so we can enforce version
   // requests as a precondition
-  MOZ_ASSERT(version == SPDY_VERSION_31 ||
-             version == HTTP_VERSION_2,
+  MOZ_ASSERT(version == HTTP_VERSION_2,
              "Unsupported spdy version");
 
   // Don't do a runtime check of IsSpdyV?Enabled() here because pref value
   // may have changed since starting negotiation. The selected protocol comes
   // from a list provided in the SERVER HELLO filtered by our acceptable
   // versions, so there is no risk of the server ignoring our prefs.
 
   Telemetry::Accumulate(Telemetry::SPDY_VERSION2, version);
 
-  if (version == SPDY_VERSION_31) {
-    return new SpdySession31(aTransport);
-  } else if (version == HTTP_VERSION_2) {
-    return new Http2Session(aTransport, version);
-  }
-
-  return nullptr;
-}
-static bool SpdySessionTrue(nsISupports *securityInfo)
-{
-  return true;
+  return new Http2Session(aTransport, version);
 }
 
 SpdyInformation::SpdyInformation()
 {
   // highest index of enabled protocols is the
   // most preferred for ALPN negotiaton
-  Version[0] = SPDY_VERSION_31;
-  VersionString[0] = NS_LITERAL_CSTRING("spdy/3.1");
-  ALPNCallbacks[0] = SpdySessionTrue;
-
-  Version[1] = HTTP_VERSION_2;
-  VersionString[1] = NS_LITERAL_CSTRING("h2");
-  ALPNCallbacks[1] = Http2Session::ALPNCallback;
+  Version[0] = HTTP_VERSION_2;
+  VersionString[0] = NS_LITERAL_CSTRING("h2");
+  ALPNCallbacks[0] = Http2Session::ALPNCallback;
 }
 
 bool
 SpdyInformation::ProtocolEnabled(uint32_t index) const
 {
   MOZ_ASSERT(index < kCount, "index out of range");
 
-  switch (index) {
-  case 0:
-    return gHttpHandler->IsSpdyV31Enabled();
-  case 1:
-    return gHttpHandler->IsHttp2Enabled();
-  }
-  return false;
+  return gHttpHandler->IsHttp2Enabled();
 }
 
 nsresult
 SpdyInformation::GetNPNIndex(const nsACString &npnString,
                              uint32_t *result) const
 {
   if (npnString.IsEmpty())
     return NS_ERROR_FAILURE;
@@ -113,47 +90,20 @@ SpdyInformation::GetNPNIndex(const nsACS
 //////////////////////////////////////////
 
 SpdyPushCache::SpdyPushCache()
 {
 }
 
 SpdyPushCache::~SpdyPushCache()
 {
-  mHashSpdy31.Clear();
   mHashHttp2.Clear();
 }
 
 bool
-SpdyPushCache::RegisterPushedStreamSpdy31(nsCString key,
-                                          SpdyPushedStream31 *stream)
-{
-  LOG3(("SpdyPushCache::RegisterPushedStreamSpdy31 %s 0x%X\n",
-        key.get(), stream->StreamID()));
-  if(mHashSpdy31.Get(key)) {
-    LOG3(("SpdyPushCache::RegisterPushedStreamSpdy31 %s 0x%X duplicate key\n",
-          key.get(), stream->StreamID()));
-    return false;
-  }
-  mHashSpdy31.Put(key, stream);
-  return true;
-}
-
-SpdyPushedStream31 *
-SpdyPushCache::RemovePushedStreamSpdy31(nsCString key)
-{
-  SpdyPushedStream31 *rv = mHashSpdy31.Get(key);
-  LOG3(("SpdyPushCache::RemovePushedStream %s 0x%X\n",
-        key.get(), rv ? rv->StreamID() : 0));
-  if (rv)
-    mHashSpdy31.Remove(key);
-  return rv;
-}
-
-bool
 SpdyPushCache::RegisterPushedStreamHttp2(nsCString key,
                                          Http2PushedStream *stream)
 {
   LOG3(("SpdyPushCache::RegisterPushedStreamHttp2 %s 0x%X\n",
         key.get(), stream->StreamID()));
   if(mHashHttp2.Get(key)) {
     LOG3(("SpdyPushCache::RegisterPushedStreamHttp2 %s 0x%X duplicate key\n",
           key.get(), stream->StreamID()));
--- a/netwerk/protocol/http/ASpdySession.h
+++ b/netwerk/protocol/http/ASpdySession.h
@@ -90,32 +90,31 @@ typedef bool (*ALPNCallback) (nsISupport
 // It could be all static except using static ctors of XPCOM objects is a
 // bad idea.
 class SpdyInformation
 {
 public:
   SpdyInformation();
   ~SpdyInformation() {}
 
-  static const uint32_t kCount = 2;
+  static const uint32_t kCount = 1;
 
   // determine the index (0..kCount-1) of the spdy information that
   // correlates to the npn string. NS_FAILED() if no match is found.
   nsresult GetNPNIndex(const nsACString &npnString, uint32_t *result) const;
 
   // determine if a version of the protocol is enabled for index < kCount
   bool ProtocolEnabled(uint32_t index) const;
 
   uint8_t   Version[kCount]; // telemetry enum e.g. SPDY_VERSION_31
   nsCString VersionString[kCount]; // npn string e.g. "spdy/3.1"
 
   // the ALPNCallback function allows the protocol stack to decide whether or
   // not to offer a particular protocol based on the known TLS information
   // that we will offer in the client hello (such as version). There has
   // not been a Server Hello received yet, so not much else can be considered.
-  // Stacks without restrictions can just use SpdySessionTrue()
   ALPNCallback ALPNCallbacks[kCount];
 };
 
 } // namespace net
 } // namespace mozilla
 
 #endif // mozilla_net_ASpdySession_h
--- a/netwerk/protocol/http/AlternateServices.cpp
+++ b/netwerk/protocol/http/AlternateServices.cpp
@@ -313,20 +313,20 @@ public:
       reason = NS_OK;
     }
 
     if (NS_FAILED(reason) || !mRunning || !mConnection) {
       LOG(("AltSvcTransaction::MaybeValidate %p Failed due to precondition", this));
       return;
     }
 
-    // insist on spdy/3* or >= http/2
+    // insist on >= http/2
     uint32_t version = mConnection->Version();
     LOG(("AltSvcTransaction::MaybeValidate() %p version %d\n", this, version));
-    if ((version < HTTP_VERSION_2) && (version != SPDY_VERSION_31)) {
+    if (version < HTTP_VERSION_2) {
       LOG(("AltSvcTransaction::MaybeValidate %p Failed due to protocol version", this));
       return;
     }
 
     nsCOMPtr<nsISupports> secInfo;
     mConnection->GetSecurityInfo(getter_AddRefs(secInfo));
     nsCOMPtr<nsISSLSocketControl> socketControl = do_QueryInterface(secInfo);
     bool bypassAuth = false;
--- a/netwerk/protocol/http/ConnectionDiagnostics.cpp
+++ b/netwerk/protocol/http/ConnectionDiagnostics.cpp
@@ -4,17 +4,16 @@
  * License, v. 2.0. If a copy of the MPL was not distributed with this
  * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
 
 // HttpLog.h should generally be included first
 #include "HttpLog.h"
 
 #include "nsHttpConnectionMgr.h"
 #include "nsHttpConnection.h"
-#include "SpdySession31.h"
 #include "Http2Session.h"
 #include "nsHttpHandler.h"
 #include "nsIConsoleService.h"
 #include "nsHttpRequestHead.h"
 #include "nsServiceManagerUtils.h"
 #include "nsSocketTransportService2.h"
 
 namespace mozilla {
@@ -153,53 +152,16 @@ nsHttpConnection::PrintDiagnostics(nsCSt
   log.AppendPrintf("    supports pipeline = %d classification = 0x%x\n",
                    mSupportsPipelining, mClassification);
 
   if (mSpdySession)
     mSpdySession->PrintDiagnostics(log);
 }
 
 void
-SpdySession31::PrintDiagnostics(nsCString &log)
-{
-  log.AppendPrintf("     ::: SPDY VERSION 3.1\n");
-  log.AppendPrintf("     shouldgoaway = %d mClosed = %d CanReuse = %d nextID=0x%X\n",
-                   mShouldGoAway, mClosed, CanReuse(), mNextStreamID);
-
-  log.AppendPrintf("     concurrent = %d maxconcurrent = %d\n",
-                   mConcurrent, mMaxConcurrent);
-
-  log.AppendPrintf("     roomformorestreams = %d roomformoreconcurrent = %d\n",
-                   RoomForMoreStreams(), RoomForMoreConcurrent());
-
-  log.AppendPrintf("     transactionHashCount = %d streamIDHashCount = %d\n",
-                   mStreamTransactionHash.Count(),
-                   mStreamIDHash.Count());
-
-  log.AppendPrintf("     Queued Stream Size = %d\n", mQueuedStreams.GetSize());
-
-  PRIntervalTime now = PR_IntervalNow();
-  log.AppendPrintf("     Ping Threshold = %ums next ping id = 0x%X\n",
-                   PR_IntervalToMilliseconds(mPingThreshold),
-                   mNextPingID);
-  log.AppendPrintf("     Ping Timeout = %ums\n",
-                   PR_IntervalToMilliseconds(gHttpHandler->SpdyPingTimeout()));
-  log.AppendPrintf("     Idle for Any Activity (ping) = %ums\n",
-                   PR_IntervalToMilliseconds(now - mLastReadEpoch));
-  log.AppendPrintf("     Idle for Data Activity = %ums\n",
-                   PR_IntervalToMilliseconds(now - mLastDataReadEpoch));
-  if (mPingSentEpoch)
-    log.AppendPrintf("     Ping Outstanding (ping) = %ums, expired = %d\n",
-                     PR_IntervalToMilliseconds(now - mPingSentEpoch),
-                     now - mPingSentEpoch >= gHttpHandler->SpdyPingTimeout());
-  else
-    log.AppendPrintf("     No Ping Outstanding\n");
-}
-
-void
 Http2Session::PrintDiagnostics(nsCString &log)
 {
   log.AppendPrintf("     ::: HTTP2\n");
   log.AppendPrintf("     shouldgoaway = %d mClosed = %d CanReuse = %d nextID=0x%X\n",
                    mShouldGoAway, mClosed, CanReuse(), mNextStreamID);
 
   log.AppendPrintf("     concurrent = %d maxconcurrent = %d\n",
                    mConcurrent, mMaxConcurrent);
--- a/netwerk/protocol/http/PSpdyPush.h
+++ b/netwerk/protocol/http/PSpdyPush.h
@@ -29,37 +29,25 @@
 #include "nsDataHashtable.h"
 #include "nsISupports.h"
 
 class nsCString;
 
 namespace mozilla {
 namespace net {
 
-class SpdyPushedStream31;
 class Http2PushedStream;
 
 // One cache per load group
 class SpdyPushCache
 {
 public:
   // The cache holds only weak pointers - no references
   SpdyPushCache();
   virtual ~SpdyPushCache();
-
-// for spdy/3.1
-public:
-  bool               RegisterPushedStreamSpdy31(nsCString key,
-                                                SpdyPushedStream31 *stream);
-  SpdyPushedStream31 *RemovePushedStreamSpdy31(nsCString key);
-private:
-  nsDataHashtable<nsCStringHashKey, SpdyPushedStream31 *> mHashSpdy31;
-
-// for http/2
-public:
   bool               RegisterPushedStreamHttp2(nsCString key,
                                                Http2PushedStream *stream);
   Http2PushedStream *RemovePushedStreamHttp2(nsCString key);
 private:
   nsDataHashtable<nsCStringHashKey, Http2PushedStream *> mHashHttp2;
 };
 
 } // namespace net
deleted file mode 100644
--- a/netwerk/protocol/http/SpdyPush31.cpp
+++ /dev/null
@@ -1,378 +0,0 @@
-/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
-/* vim: set sw=2 ts=8 et tw=80 : */
-/* This Source Code Form is subject to the terms of the Mozilla Public
- * License, v. 2.0. If a copy of the MPL was not distributed with this
- * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
-
-// HttpLog.h should generally be included first
-#include "HttpLog.h"
-
-// Log on level :5, instead of default :4.
-#undef LOG
-#define LOG(args) LOG5(args)
-#undef LOG_ENABLED
-#define LOG_ENABLED() LOG5_ENABLED()
-
-#include <algorithm>
-
-#include "nsDependentString.h"
-#include "SpdyPush31.h"
-
-namespace mozilla {
-namespace net {
-
-//////////////////////////////////////////
-// SpdyPushedStream31
-//////////////////////////////////////////
-
-SpdyPushedStream31::SpdyPushedStream31(SpdyPush31TransactionBuffer *aTransaction,
-                                       SpdySession31 *aSession,
-                                       SpdyStream31 *aAssociatedStream,
-                                       uint32_t aID)
-  :SpdyStream31(aTransaction, aSession,
-                0 /* priority is only for sending, so ignore it on push */)
-  , mConsumerStream(nullptr)
-  , mBufferedPush(aTransaction)
-  , mStatus(NS_OK)
-  , mPushCompleted(false)
-  , mDeferCleanupOnSuccess(true)
-{
-  LOG3(("SpdyPushedStream31 ctor this=%p id=0x%X\n", this, aID));
-  mStreamID = aID;
-  mBufferedPush->SetPushStream(this);
-  mRequestContext = aAssociatedStream->RequestContext();
-  mLastRead = TimeStamp::Now();
-}
-
-bool
-SpdyPushedStream31::GetPushComplete()
-{
-  return mPushCompleted;
-}
-
-nsresult
-SpdyPushedStream31::WriteSegments(nsAHttpSegmentWriter *writer,
-                                  uint32_t count,
-                                  uint32_t *countWritten)
-{
-  nsresult rv = SpdyStream31::WriteSegments(writer, count, countWritten);
-  if (NS_SUCCEEDED(rv) && *countWritten) {
-    mLastRead = TimeStamp::Now();
-  }
-
-  if (rv == NS_BASE_STREAM_CLOSED) {
-    mPushCompleted = true;
-    rv = NS_OK; // this is what a normal HTTP transaction would do
-  }
-  if (rv != NS_BASE_STREAM_WOULD_BLOCK && NS_FAILED(rv))
-    mStatus = rv;
-  return rv;
-}
-
-nsresult
-SpdyPushedStream31::ReadSegments(nsAHttpSegmentReader *,  uint32_t, uint32_t *count)
-{
-  // The SYN_STREAM for this has been processed, so we need to verify
-  // that :host, :scheme, and :path MUST be present
-  nsDependentCSubstring host, scheme, path;
-  nsresult rv;
-
-  rv = SpdyStream31::FindHeader(NS_LITERAL_CSTRING(":host"), host);
-  if (NS_FAILED(rv)) {
-    LOG3(("SpdyPushedStream31::ReadSegments session=%p ID 0x%X "
-          "push without required :host\n", mSession, mStreamID));
-    return rv;
-  }
-
-  rv = SpdyStream31::FindHeader(NS_LITERAL_CSTRING(":scheme"), scheme);
-  if (NS_FAILED(rv)) {
-    LOG3(("SpdyPushedStream31::ReadSegments session=%p ID 0x%X "
-          "push without required :scheme\n", mSession, mStreamID));
-    return rv;
-  }
-
-  rv = SpdyStream31::FindHeader(NS_LITERAL_CSTRING(":path"), path);
-  if (NS_FAILED(rv)) {
-    LOG3(("SpdyPushedStream31::ReadSegments session=%p ID 0x%X "
-          "push without required :host\n", mSession, mStreamID));
-    return rv;
-  }
-
-  CreatePushHashKey(nsCString(scheme), nsCString(host),
-                    mSession->Serial(), path,
-                    mOrigin, mHashKey);
-
-  LOG3(("SpdyPushStream31 0x%X hash key %s\n", mStreamID, mHashKey.get()));
-
-  // the write side of a pushed transaction just involves manipulating a little state
-  SpdyStream31::mSentFinOnData = 1;
-  SpdyStream31::mRequestHeadersDone = 1;
-  SpdyStream31::mSynFrameGenerated = 1;
-  SpdyStream31::ChangeState(UPSTREAM_COMPLETE);
-  *count = 0;
-  return NS_OK;
-}
-
-bool
-SpdyPushedStream31::GetHashKey(nsCString &key)
-{
-  if (mHashKey.IsEmpty())
-    return false;
-
-  key = mHashKey;
-  return true;
-}
-
-void
-SpdyPushedStream31::ConnectPushedStream(SpdyStream31 *stream)
-{
-  mSession->ConnectPushedStream(stream);
-}
-
-bool
-SpdyPushedStream31::IsOrphaned(TimeStamp now)
-{
-  MOZ_ASSERT(!now.IsNull());
-
-  // if spdy is not transmitting, and is also not connected to a consumer
-  // stream, and its been like that for too long then it is oprhaned
-
-  if (mConsumerStream)
-    return false;
-
-  bool rv = ((now - mLastRead).ToSeconds() > 30.0);
-  if (rv) {
-    LOG3(("SpdyPushedStream31::IsOrphaned 0x%X IsOrphaned %3.2f\n",
-          mStreamID, (now - mLastRead).ToSeconds()));
-  }
-  return rv;
-}
-
-nsresult
-SpdyPushedStream31::GetBufferedData(char *buf,
-                                    uint32_t count,
-                                    uint32_t *countWritten)
-{
-  if (NS_FAILED(mStatus))
-    return mStatus;
-
-  nsresult rv = mBufferedPush->GetBufferedData(buf, count, countWritten);
-  if (NS_FAILED(rv))
-    return rv;
-
-  if (!*countWritten)
-    rv = GetPushComplete() ? NS_BASE_STREAM_CLOSED : NS_BASE_STREAM_WOULD_BLOCK;
-
-  return rv;
-}
-
-//////////////////////////////////////////
-// SpdyPush31TransactionBuffer
-// This is the nsAHttpTransction owned by the stream when the pushed
-// stream has not yet been matched with a pull request
-//////////////////////////////////////////
-
-NS_IMPL_ISUPPORTS0(SpdyPush31TransactionBuffer)
-
-SpdyPush31TransactionBuffer::SpdyPush31TransactionBuffer()
-  : mStatus(NS_OK)
-  , mRequestHead(nullptr)
-  , mPushStream(nullptr)
-  , mIsDone(false)
-  , mBufferedHTTP1Size(kDefaultBufferSize)
-  , mBufferedHTTP1Used(0)
-  , mBufferedHTTP1Consumed(0)
-{
-  mBufferedHTTP1 = MakeUnique<char[]>(mBufferedHTTP1Size);
-}
-
-SpdyPush31TransactionBuffer::~SpdyPush31TransactionBuffer()
-{
-  delete mRequestHead;
-}
-
-void
-SpdyPush31TransactionBuffer::SetConnection(nsAHttpConnection *conn)
-{
-}
-
-nsAHttpConnection *
-SpdyPush31TransactionBuffer::Connection()
-{
-  return nullptr;
-}
-
-void
-SpdyPush31TransactionBuffer::GetSecurityCallbacks(nsIInterfaceRequestor **outCB)
-{
-  *outCB = nullptr;
-}
-
-void
-SpdyPush31TransactionBuffer::OnTransportStatus(nsITransport* transport,
-                                               nsresult status, int64_t progress)
-{
-}
-
-nsHttpConnectionInfo *
-SpdyPush31TransactionBuffer::ConnectionInfo()
-{
-  if (!mPushStream) {
-    return nullptr;
-  }
-  if (!mPushStream->Transaction()) {
-    return nullptr;
-  }
-  MOZ_ASSERT(mPushStream->Transaction() != this);
-  return mPushStream->Transaction()->ConnectionInfo();
-}
-
-bool
-SpdyPush31TransactionBuffer::IsDone()
-{
-  return mIsDone;
-}
-
-nsresult
-SpdyPush31TransactionBuffer::Status()
-{
-  return mStatus;
-}
-
-uint32_t
-SpdyPush31TransactionBuffer::Caps()
-{
-  return 0;
-}
-
-void
-SpdyPush31TransactionBuffer::SetDNSWasRefreshed()
-{
-}
-
-uint64_t
-SpdyPush31TransactionBuffer::Available()
-{
-  return mBufferedHTTP1Used - mBufferedHTTP1Consumed;
-}
-
-nsresult
-SpdyPush31TransactionBuffer::ReadSegments(nsAHttpSegmentReader *reader,
-                                            uint32_t count, uint32_t *countRead)
-{
-  *countRead = 0;
-  return NS_ERROR_NOT_IMPLEMENTED;
-}
-
-nsresult
-SpdyPush31TransactionBuffer::WriteSegments(nsAHttpSegmentWriter *writer,
-                                           uint32_t count, uint32_t *countWritten)
-{
-  if ((mBufferedHTTP1Size - mBufferedHTTP1Used) < 20480) {
-    EnsureBuffer(mBufferedHTTP1, mBufferedHTTP1Size + kDefaultBufferSize,
-                 mBufferedHTTP1Used, mBufferedHTTP1Size);
-  }
-
-  count = std::min(count, mBufferedHTTP1Size - mBufferedHTTP1Used);
-  nsresult rv = writer->OnWriteSegment(&mBufferedHTTP1[mBufferedHTTP1Used],
-                                       count, countWritten);
-  if (NS_SUCCEEDED(rv)) {
-    mBufferedHTTP1Used += *countWritten;
-  }
-  else if (rv == NS_BASE_STREAM_CLOSED) {
-    mIsDone = true;
-  }
-
-  if (Available() || mIsDone) {
-    SpdyStream31 *consumer = mPushStream->GetConsumerStream();
-
-    if (consumer) {
-      LOG3(("SpdyPush31TransactionBuffer::WriteSegments notifying connection "
-            "consumer data available 0x%X [%u] done=%d\n",
-            mPushStream->StreamID(), Available(), mIsDone));
-      mPushStream->ConnectPushedStream(consumer);
-    }
-  }
-
-  return rv;
-}
-
-uint32_t
-SpdyPush31TransactionBuffer::Http1xTransactionCount()
-{
-  return 0;
-}
-
-nsHttpRequestHead *
-SpdyPush31TransactionBuffer::RequestHead()
-{
-  if (!mRequestHead)
-    mRequestHead = new nsHttpRequestHead();
-  return mRequestHead;
-}
-
-nsresult
-SpdyPush31TransactionBuffer::TakeSubTransactions(
-  nsTArray<RefPtr<nsAHttpTransaction> > &outTransactions)
-{
-  return NS_ERROR_NOT_IMPLEMENTED;
-}
-
-void
-SpdyPush31TransactionBuffer::SetProxyConnectFailed()
-{
-}
-
-void
-SpdyPush31TransactionBuffer::Close(nsresult reason)
-{
-  mStatus = reason;
-  mIsDone = true;
-}
-
-nsresult
-SpdyPush31TransactionBuffer::AddTransaction(nsAHttpTransaction *trans)
-{
-  return NS_ERROR_NOT_IMPLEMENTED;
-}
-
-uint32_t
-SpdyPush31TransactionBuffer::PipelineDepth()
-{
-  return 0;
-}
-
-nsresult
-SpdyPush31TransactionBuffer::SetPipelinePosition(int32_t position)
-{
-  return NS_OK;
-}
-
-int32_t
-SpdyPush31TransactionBuffer::PipelinePosition()
-{
-  return 1;
-}
-
-nsresult
-SpdyPush31TransactionBuffer::GetBufferedData(char *buf,
-                                               uint32_t count,
-                                               uint32_t *countWritten)
-{
-  *countWritten = std::min(count, static_cast<uint32_t>(Available()));
-  if (*countWritten) {
-    memcpy(buf, &mBufferedHTTP1[mBufferedHTTP1Consumed], *countWritten);
-    mBufferedHTTP1Consumed += *countWritten;
-  }
-
-  // If all the data has been consumed then reset the buffer
-  if (mBufferedHTTP1Consumed == mBufferedHTTP1Used) {
-    mBufferedHTTP1Consumed = 0;
-    mBufferedHTTP1Used = 0;
-  }
-
-  return NS_OK;
-}
-
-} // namespace net
-} // namespace mozilla
deleted file mode 100644
--- a/netwerk/protocol/http/SpdyPush31.h
+++ /dev/null
@@ -1,103 +0,0 @@
-/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
-/* This Source Code Form is subject to the terms of the Mozilla Public
- * License, v. 2.0. If a copy of the MPL was not distributed with this
- * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
-
-// spdy/3.1
-
-#ifndef mozilla_net_SpdyPush31_Internal_h
-#define mozilla_net_SpdyPush31_Internal_h
-
-#include "mozilla/Attributes.h"
-#include "mozilla/TimeStamp.h"
-#include "mozilla/UniquePtr.h"
-#include "nsHttpRequestHead.h"
-#include "nsIRequestContext.h"
-#include "nsString.h"
-#include "PSpdyPush.h"
-#include "SpdySession31.h"
-#include "SpdyStream31.h"
-
-namespace mozilla {
-namespace net {
-
-class SpdyPush31TransactionBuffer;
-
-class SpdyPushedStream31 final : public SpdyStream31
-{
-public:
-  SpdyPushedStream31(SpdyPush31TransactionBuffer *aTransaction,
-                     SpdySession31 *aSession,
-                     SpdyStream31 *aAssociatedStream,
-                     uint32_t aID);
-  virtual ~SpdyPushedStream31() {}
-
-  bool GetPushComplete();
-  SpdyStream31 *GetConsumerStream() { return mConsumerStream; };
-  void SetConsumerStream(SpdyStream31 *aStream) { mConsumerStream = aStream; }
-  bool GetHashKey(nsCString &key);
-
-  // override of SpdyStream31
-  nsresult ReadSegments(nsAHttpSegmentReader *,  uint32_t, uint32_t *);
-  nsresult WriteSegments(nsAHttpSegmentWriter *, uint32_t, uint32_t *);
-
-  nsIRequestContext *RequestContext() { return mRequestContext; };
-  void ConnectPushedStream(SpdyStream31 *consumer);
-
-  bool DeferCleanupOnSuccess() { return mDeferCleanupOnSuccess; }
-  void SetDeferCleanupOnSuccess(bool val) { mDeferCleanupOnSuccess = val; }
-
-  bool IsOrphaned(TimeStamp now);
-
-  nsresult GetBufferedData(char *buf, uint32_t count, uint32_t *countWritten);
-
-  // overload of SpdyStream31
-  virtual bool HasSink() { return !!mConsumerStream; }
-
-private:
-
-  SpdyStream31 *mConsumerStream; // paired request stream that consumes from
-  // real spdy one.. null until a match is made.
-
-  nsCOMPtr<nsIRequestContext> mRequestContext;
-
-  SpdyPush31TransactionBuffer *mBufferedPush;
-  TimeStamp          mLastRead;
-
-  nsCString mHashKey;
-  nsresult mStatus;
-  bool mPushCompleted; // server push FIN received
-  bool mDeferCleanupOnSuccess;
-};
-
-class SpdyPush31TransactionBuffer final : public nsAHttpTransaction
-{
-public:
-  NS_DECL_ISUPPORTS
-  NS_DECL_NSAHTTPTRANSACTION
-
-  SpdyPush31TransactionBuffer();
-
-  nsresult GetBufferedData(char *buf, uint32_t count, uint32_t *countWritten);
-  void SetPushStream(SpdyPushedStream31 *stream) { mPushStream = stream; }
-
-private:
-  virtual ~SpdyPush31TransactionBuffer();
-
-  const static uint32_t kDefaultBufferSize = 4096;
-
-  nsresult mStatus;
-  nsHttpRequestHead *mRequestHead;
-  SpdyPushedStream31 *mPushStream;
-  bool mIsDone;
-
-  UniquePtr<char[]> mBufferedHTTP1;
-  uint32_t mBufferedHTTP1Size;
-  uint32_t mBufferedHTTP1Used;
-  uint32_t mBufferedHTTP1Consumed;
-};
-
-} // namespace net
-} // namespace mozilla
-
-#endif // mozilla_net_SpdyPush3_Internal_h
deleted file mode 100644
--- a/netwerk/protocol/http/SpdySession31.cpp
+++ /dev/null
@@ -1,3077 +0,0 @@
-/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
-/* vim: set sw=2 ts=8 et tw=80 : */
-/* This Source Code Form is subject to the terms of the Mozilla Public
- * License, v. 2.0. If a copy of the MPL was not distributed with this
- * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
-
-// HttpLog.h should generally be included first
-#include "HttpLog.h"
-
-// Log on level :5, instead of default :4.
-#undef LOG
-#define LOG(args) LOG5(args)
-#undef LOG_ENABLED
-#define LOG_ENABLED() LOG5_ENABLED()
-
-#include "mozilla/Telemetry.h"
-#include "mozilla/Preferences.h"
-#include "mozilla/Snprintf.h"
-#include "nsHttp.h"
-#include "nsHttpHandler.h"
-#include "nsHttpConnection.h"
-#include "nsIRequestContext.h"
-#include "nsISupportsPriority.h"
-#include "prnetdb.h"
-#include "SpdyPush31.h"
-#include "SpdySession31.h"
-#include "SpdyStream31.h"
-#include "SpdyZlibReporter.h"
-#include "nsSocketTransportService2.h"
-
-#include <algorithm>
-
-namespace mozilla {
-namespace net {
-
-// SpdySession31 has multiple inheritance of things that implement
-// nsISupports, so this magic is taken from nsHttpPipeline that
-// implements some of the same abstract classes.
-NS_IMPL_ADDREF(SpdySession31)
-NS_IMPL_RELEASE(SpdySession31)
-NS_INTERFACE_MAP_BEGIN(SpdySession31)
-NS_INTERFACE_MAP_ENTRY_AMBIGUOUS(nsISupports, nsAHttpConnection)
-NS_INTERFACE_MAP_END
-
-SpdySession31::SpdySession31(nsISocketTransport *aSocketTransport)
-  : mSocketTransport(aSocketTransport)
-  , mSegmentReader(nullptr)
-  , mSegmentWriter(nullptr)
-  , mNextStreamID(1)
-  , mConcurrentHighWater(0)
-  , mDownstreamState(BUFFERING_FRAME_HEADER)
-  , mInputFrameBufferSize(kDefaultBufferSize)
-  , mInputFrameBufferUsed(0)
-  , mInputFrameDataLast(false)
-  , mInputFrameDataStream(nullptr)
-  , mNeedsCleanup(nullptr)
-  , mShouldGoAway(false)
-  , mClosed(false)
-  , mCleanShutdown(false)
-  , mDataPending(false)
-  , mGoAwayID(0)
-  , mConcurrent(0)
-  , mServerPushedResources(0)
-  , mServerInitialStreamWindow(kDefaultRwin)
-  , mLocalSessionWindow(kDefaultRwin)
-  , mRemoteSessionWindow(kDefaultRwin)
-  , mOutputQueueSize(kDefaultQueueSize)
-  , mOutputQueueUsed(0)
-  , mOutputQueueSent(0)
-  , mLastReadEpoch(PR_IntervalNow())
-  , mPingSentEpoch(0)
-  , mNextPingID(1)
-  , mPreviousUsed(false)
-{
-  MOZ_ASSERT(PR_GetCurrentThread() == gSocketThread);
-
-  static uint64_t sSerial;
-  mSerial = ++sSerial;
-
-  LOG3(("SpdySession31::SpdySession31 %p serial=0x%X\n", this, mSerial));
-
-  mInputFrameBuffer = MakeUnique<char[]>(mInputFrameBufferSize);
-  mOutputQueueBuffer = MakeUnique<char[]>(mOutputQueueSize);
-  zlibInit();
-
-  mPushAllowance = gHttpHandler->SpdyPushAllowance();
-  mMaxConcurrent = gHttpHandler->DefaultSpdyConcurrent();
-  mSendingChunkSize = gHttpHandler->SpdySendingChunkSize();
-  GenerateSettings();
-
-  mLastDataReadEpoch = mLastReadEpoch;
-
-  mPingThreshold = gHttpHandler->SpdyPingThreshold();
-}
-
-void
-SpdySession31::Shutdown()
-{
-  for (auto iter = mStreamTransactionHash.Iter(); !iter.Done(); iter.Next()) {
-    nsAutoPtr<SpdyStream31>& stream = iter.Data();
-
-    // On a clean server hangup the server sets the GoAwayID to be the ID of
-    // the last transaction it processed. If the ID of stream in the
-    // local stream is greater than that it can safely be restarted because the
-    // server guarantees it was not partially processed. Streams that have not
-    // registered an ID haven't actually been sent yet so they can always be
-    // restarted.
-    if (mCleanShutdown &&
-        (stream->StreamID() > mGoAwayID || !stream->HasRegisteredID())) {
-      CloseStream(stream, NS_ERROR_NET_RESET); // can be restarted
-    } else {
-      CloseStream(stream, NS_ERROR_ABORT);
-    }
-  }
-}
-
-SpdySession31::~SpdySession31()
-{
-  LOG3(("SpdySession31::~SpdySession31 %p mDownstreamState=%X",
-        this, mDownstreamState));
-
-  inflateEnd(&mDownstreamZlib);
-  deflateEnd(&mUpstreamZlib);
-
-  Shutdown();
-
-  Telemetry::Accumulate(Telemetry::SPDY_PARALLEL_STREAMS, mConcurrentHighWater);
-  Telemetry::Accumulate(Telemetry::SPDY_REQUEST_PER_CONN, (mNextStreamID - 1) / 2);
-  Telemetry::Accumulate(Telemetry::SPDY_SERVER_INITIATED_STREAMS,
-                        mServerPushedResources);
-}
-
-void
-SpdySession31::LogIO(SpdySession31 *self, SpdyStream31 *stream, const char *label,
-                     const char *data, uint32_t datalen)
-{
-  if (!LOG5_ENABLED())
-    return;
-
-  LOG5(("SpdySession31::LogIO %p stream=%p id=0x%X [%s]",
-        self, stream, stream ? stream->StreamID() : 0, label));
-
-  // Max line is (16 * 3) + 10(prefix) + newline + null
-  char linebuf[128];
-  uint32_t index;
-  char *line = linebuf;
-
-  linebuf[127] = 0;
-
-  for (index = 0; index < datalen; ++index) {
-    if (!(index % 16)) {
-      if (index) {
-        *line = 0;
-        LOG5(("%s", linebuf));
-      }
-      line = linebuf;
-      snprintf(line, 128, "%08X: ", index);
-      line += 10;
-    }
-    snprintf(line, 128 - (line - linebuf), "%02X ", ((unsigned char *)data)[index]);
-    line += 3;
-  }
-  if (index) {
-    *line = 0;
-    LOG5(("%s", linebuf));
-  }
-}
-
-bool
-SpdySession31::RoomForMoreConcurrent()
-{
-  MOZ_ASSERT(PR_GetCurrentThread() == gSocketThread);
-
-  return (mConcurrent < mMaxConcurrent);
-}
-
-bool
-SpdySession31::RoomForMoreStreams()
-{
-  if (mNextStreamID + mStreamTransactionHash.Count() * 2 > kMaxStreamID)
-    return false;
-
-  return !mShouldGoAway;
-}
-
-PRIntervalTime
-SpdySession31::IdleTime()
-{
-  return PR_IntervalNow() - mLastDataReadEpoch;
-}
-
-uint32_t
-SpdySession31::ReadTimeoutTick(PRIntervalTime now)
-{
-  MOZ_ASSERT(PR_GetCurrentThread() == gSocketThread);
-  MOZ_ASSERT(mNextPingID & 1, "Ping Counter Not Odd");
-
-  LOG(("SpdySession31::ReadTimeoutTick %p delta since last read %ds\n",
-       this, PR_IntervalToSeconds(now - mLastReadEpoch)));
-
-  if (!mPingThreshold)
-    return UINT32_MAX;
-
-  if ((now - mLastReadEpoch) < mPingThreshold) {
-    // recent activity means ping is not an issue
-    if (mPingSentEpoch) {
-      mPingSentEpoch = 0;
-      if (mPreviousUsed) {
-        // restore the former value
-        mPingThreshold = mPreviousPingThreshold;
-        mPreviousUsed = false;
-      }
-    }
-
-    return PR_IntervalToSeconds(mPingThreshold) -
-      PR_IntervalToSeconds(now - mLastReadEpoch);
-  }
-
-  if (mPingSentEpoch) {
-    LOG(("SpdySession31::ReadTimeoutTick %p handle outstanding ping\n", this));
-    if ((now - mPingSentEpoch) >= gHttpHandler->SpdyPingTimeout()) {
-      LOG(("SpdySession31::ReadTimeoutTick %p Ping Timer Exhaustion\n",
-           this));
-      mPingSentEpoch = 0;
-      Close(NS_ERROR_NET_TIMEOUT);
-      return UINT32_MAX;
-    }
-    return 1; // run the tick aggressively while ping is outstanding
-  }
-
-  LOG(("SpdySession31::ReadTimeoutTick %p generating ping 0x%X\n",
-       this, mNextPingID));
-
-  if (mNextPingID == 0xffffffff) {
-    LOG(("SpdySession31::ReadTimeoutTick %p cannot form ping - ids exhausted\n",
-         this));
-    return UINT32_MAX;
-  }
-
-  mPingSentEpoch = PR_IntervalNow();
-  if (!mPingSentEpoch)
-    mPingSentEpoch = 1; // avoid the 0 sentinel value
-  GeneratePing(mNextPingID);
-  mNextPingID += 2;
-  ResumeRecv(); // read the ping reply
-
-  // Check for orphaned push streams. This looks expensive, but generally the
-  // list is empty.
-  SpdyPushedStream31 *deleteMe;
-  TimeStamp timestampNow;
-  do {
-    deleteMe = nullptr;
-
-    for (uint32_t index = mPushedStreams.Length();
-         index > 0 ; --index) {
-      SpdyPushedStream31 *pushedStream = mPushedStreams[index - 1];
-
-      if (timestampNow.IsNull())
-        timestampNow = TimeStamp::Now(); // lazy initializer
-
-      // if spdy finished, but not connected, and its been like that for too long..
-      // cleanup the stream..
-      if (pushedStream->IsOrphaned(timestampNow))
-      {
-        LOG3(("SpdySession31 Timeout Pushed Stream %p 0x%X\n",
-              this, pushedStream->StreamID()));
-        deleteMe = pushedStream;
-        break; // don't CleanupStream() while iterating this vector
-      }
-    }
-    if (deleteMe)
-      CleanupStream(deleteMe, NS_ERROR_ABORT, RST_CANCEL);
-
-  } while (deleteMe);
-
-  if (mNextPingID == 0xffffffff) {
-    LOG(("SpdySession31::ReadTimeoutTick %p "
-         "ping ids exhausted marking goaway\n", this));
-    mShouldGoAway = true;
-  }
-  return 1; // run the tick aggressively while ping is outstanding
-}
-
-uint32_t
-SpdySession31::RegisterStreamID(SpdyStream31 *stream, uint32_t aNewID)
-{
-  MOZ_ASSERT(PR_GetCurrentThread() == gSocketThread);
-
-  MOZ_ASSERT(mNextStreamID < 0xfffffff0,
-             "should have stopped admitting streams");
-
-  MOZ_ASSERT(!(aNewID & 1),
-             "0 for autoassign pull, otherwise explicit even push assignment");
-  if (!aNewID) {
-    // auto generate a new pull stream ID
-    aNewID = mNextStreamID;
-    MOZ_ASSERT(aNewID & 1, "pull ID must be odd.");
-    mNextStreamID += 2;
-  }
-
-  LOG3(("SpdySession31::RegisterStreamID session=%p stream=%p id=0x%X "
-        "concurrent=%d",this, stream, aNewID, mConcurrent));
-
-  // We've used up plenty of ID's on this session. Start
-  // moving to a new one before there is a crunch involving
-  // server push streams or concurrent non-registered submits
-  if (aNewID >= kMaxStreamID)
-    mShouldGoAway = true;
-
-  // integrity check
-  if (mStreamIDHash.Get(aNewID)) {
-    LOG3(("   New ID already present\n"));
-    MOZ_ASSERT(false, "New ID already present in mStreamIDHash");
-    mShouldGoAway = true;
-    return kDeadStreamID;
-  }
-
-  mStreamIDHash.Put(aNewID, stream);
-  return aNewID;
-}
-
-bool
-SpdySession31::AddStream(nsAHttpTransaction *aHttpTransaction,
-                         int32_t aPriority,
-                         bool aUseTunnel,
-                         nsIInterfaceRequestor *aCallbacks)
-{
-  MOZ_ASSERT(PR_GetCurrentThread() == gSocketThread);
-
-  // integrity check
-  if (mStreamTransactionHash.Get(aHttpTransaction)) {
-    LOG3(("   New transaction already present\n"));
-    MOZ_ASSERT(false, "AddStream duplicate transaction pointer");
-    return false;
-  }
-
-  if (!mConnection) {
-    mConnection = aHttpTransaction->Connection();
-  }
-
-  if (mClosed || mShouldGoAway) {
-    nsHttpTransaction *trans = aHttpTransaction->QueryHttpTransaction();
-    if (trans && !trans->GetPushedStream()) {
-      LOG3(("SpdySession31::AddStream %p atrans=%p trans=%p session unusable - resched.\n",
-            this, aHttpTransaction, trans));
-      aHttpTransaction->SetConnection(nullptr);
-      gHttpHandler->InitiateTransaction(trans, trans->Priority());
-      return true;
-    }
-  }
-
-  aHttpTransaction->SetConnection(this);
-
-  if (aUseTunnel) {
-    LOG3(("SpdySession31::AddStream session=%p trans=%p OnTunnel",
-          this, aHttpTransaction));
-    DispatchOnTunnel(aHttpTransaction, aCallbacks);
-    return true;
-  }
-
-  SpdyStream31 *stream = new SpdyStream31(aHttpTransaction, this, aPriority);
-
-  LOG3(("SpdySession31::AddStream session=%p stream=%p serial=%u "
-        "NextID=0x%X (tentative)", this, stream, mSerial, mNextStreamID));
-
-  mStreamTransactionHash.Put(aHttpTransaction, stream);
-
-  mReadyForWrite.Push(stream);
-  SetWriteCallbacks();
-
-  // Kick off the SYN transmit without waiting for the poll loop
-  // This won't work for stream id=1 because there is no segment reader
-  // yet.
-  if (mSegmentReader) {
-    uint32_t countRead;
-    ReadSegments(nullptr, kDefaultBufferSize, &countRead);
-  }
-
-  if (!(aHttpTransaction->Caps() & NS_HTTP_ALLOW_KEEPALIVE) &&
-      !aHttpTransaction->IsNullTransaction()) {
-    LOG3(("SpdySession31::AddStream %p transaction %p forces keep-alive off.\n",
-          this, aHttpTransaction));
-    DontReuse();
-  }
-
-  return true;
-}
-
-void
-SpdySession31::QueueStream(SpdyStream31 *stream)
-{
-  // will be removed via processpending or a shutdown path
-  MOZ_ASSERT(PR_GetCurrentThread() == gSocketThread);
-  MOZ_ASSERT(!stream->CountAsActive());
-  MOZ_ASSERT(!stream->Queued());
-
-  LOG3(("SpdySession31::QueueStream %p stream %p queued.", this, stream));
-
-#ifdef DEBUG
-  size_t qsize = mQueuedStreams.GetSize();
-  for (size_t i = 0; i < qsize; i++) {
-    SpdyStream31 *qStream = static_cast<SpdyStream31 *>(mQueuedStreams.ObjectAt(i));
-    MOZ_ASSERT(qStream != stream);
-    MOZ_ASSERT(qStream->Queued());
-  }
-#endif
-
-  stream->SetQueued(true);
-  mQueuedStreams.Push(stream);
-}
-
-void
-SpdySession31::ProcessPending()
-{
-  MOZ_ASSERT(PR_GetCurrentThread() == gSocketThread);
-
-  SpdyStream31 *stream;
-  while (RoomForMoreConcurrent() &&
-         (stream = static_cast<SpdyStream31 *>(mQueuedStreams.PopFront()))) {
-
-    LOG3(("SpdySession31::ProcessPending %p stream %p woken from queue.",
-          this, stream));
-    MOZ_ASSERT(!stream->CountAsActive());
-    MOZ_ASSERT(stream->Queued());
-    stream->SetQueued(false);
-    mReadyForWrite.Push(stream);
-    SetWriteCallbacks();
-  }
-}
-
-nsresult
-SpdySession31::NetworkRead(nsAHttpSegmentWriter *writer, char *buf,
-                           uint32_t count, uint32_t *countWritten)
-{
-  MOZ_ASSERT(PR_GetCurrentThread() == gSocketThread);
-
-  if (!count) {
-    *countWritten = 0;
-    return NS_OK;
-  }
-
-  nsresult rv = writer->OnWriteSegment(buf, count, countWritten);
-  if (NS_SUCCEEDED(rv) && *countWritten > 0)
-    mLastReadEpoch = PR_IntervalNow();
-  return rv;
-}
-
-void
-SpdySession31::SetWriteCallbacks()
-{
-  if (mConnection && (GetWriteQueueSize() || mOutputQueueUsed))
-    mConnection->ResumeSend();
-}
-
-void
-SpdySession31::RealignOutputQueue()
-{
-  mOutputQueueUsed -= mOutputQueueSent;
-  memmove(mOutputQueueBuffer.get(),
-          mOutputQueueBuffer.get() + mOutputQueueSent,
-          mOutputQueueUsed);
-  mOutputQueueSent = 0;
-}
-
-void
-SpdySession31::FlushOutputQueue()
-{
-  if (!mSegmentReader || !mOutputQueueUsed)
-    return;
-
-  nsresult rv;
-  uint32_t countRead;
-  uint32_t avail = mOutputQueueUsed - mOutputQueueSent;
-
-  rv = mSegmentReader->
-    OnReadSegment(mOutputQueueBuffer.get() + mOutputQueueSent, avail,
-                  &countRead);
-  LOG3(("SpdySession31::FlushOutputQueue %p sz=%d rv=%x actual=%d",
-        this, avail, rv, countRead));
-
-  // Dont worry about errors on write, we will pick this up as a read error too
-  if (NS_FAILED(rv))
-    return;
-
-  if (countRead == avail) {
-    mOutputQueueUsed = 0;
-    mOutputQueueSent = 0;
-    return;
-  }
-
-  mOutputQueueSent += countRead;
-
-  // If the output queue is close to filling up and we have sent out a good
-  // chunk of data from the beginning then realign it.
-
-  if ((mOutputQueueSent >= kQueueMinimumCleanup) &&
-      ((mOutputQueueSize - mOutputQueueUsed) < kQueueTailRoom)) {
-    RealignOutputQueue();
-  }
-}
-
-void
-SpdySession31::DontReuse()
-{
-  mShouldGoAway = true;
-  if (!mStreamTransactionHash.Count())
-    Close(NS_OK);
-}
-
-uint32_t
-SpdySession31::GetWriteQueueSize()
-{
-  MOZ_ASSERT(PR_GetCurrentThread() == gSocketThread);
-
-  return mReadyForWrite.GetSize();
-}
-
-void
-SpdySession31::ChangeDownstreamState(enum stateType newState)
-{
-  MOZ_ASSERT(PR_GetCurrentThread() == gSocketThread);
-
-  LOG3(("SpdySession31::ChangeDownstreamState() %p from %X to %X",
-        this, mDownstreamState, newState));
-  mDownstreamState = newState;
-}
-
-void
-SpdySession31::ResetDownstreamState()
-{
-  MOZ_ASSERT(PR_GetCurrentThread() == gSocketThread);
-
-  LOG3(("SpdySession31::ResetDownstreamState() %p", this));
-  ChangeDownstreamState(BUFFERING_FRAME_HEADER);
-
-  if (mInputFrameDataLast && mInputFrameDataStream) {
-    mInputFrameDataLast = false;
-    if (!mInputFrameDataStream->RecvdFin()) {
-      LOG3(("  SetRecvdFin id=0x%x\n", mInputFrameDataStream->StreamID()));
-      mInputFrameDataStream->SetRecvdFin(true);
-      DecrementConcurrent(mInputFrameDataStream);
-    }
-  }
-  mInputFrameDataLast = false;
-  mInputFrameBufferUsed = 0;
-  mInputFrameDataStream = nullptr;
-}
-
-// return true if activated (and counted against max)
-// otherwise return false and queue
-bool
-SpdySession31::TryToActivate(SpdyStream31 *aStream)
-{
-  if (aStream->Queued()) {
-    LOG3(("SpdySession31::TryToActivate %p stream=%p already queued.\n", this, aStream));
-    return false;
-  }
-
-  if (!RoomForMoreConcurrent()) {
-    LOG3(("SpdySession31::TryToActivate %p stream=%p no room for more concurrent "
-          "streams %d\n", this, aStream));
-    QueueStream(aStream);
-    return false;
-  }
-
-  LOG3(("SpdySession31::TryToActivate %p stream=%p\n", this, aStream));
-  IncrementConcurrent(aStream);
-  return true;
-}
-
-void
-SpdySession31::IncrementConcurrent(SpdyStream31 *stream)
-{
-  MOZ_ASSERT(PR_GetCurrentThread() == gSocketThread);
-  MOZ_ASSERT(!stream->StreamID() || (stream->StreamID() & 1),
-             "Do not activate pushed streams");
-
-  nsAHttpTransaction *trans = stream->Transaction();
-  if (!trans || !trans->IsNullTransaction() || trans->QuerySpdyConnectTransaction()) {
-
-    MOZ_ASSERT(!stream->CountAsActive());
-    stream->SetCountAsActive(true);
-    ++mConcurrent;
-
-    if (mConcurrent > mConcurrentHighWater) {
-      mConcurrentHighWater = mConcurrent;
-    }
-    LOG3(("SpdySession31::AddStream %p counting stream %p Currently %d "
-          "streams in session, high water mark is %d",
-          this, stream, mConcurrent, mConcurrentHighWater));
-  }
-}
-
-void
-SpdySession31::DecrementConcurrent(SpdyStream31 *aStream)
-{
-  MOZ_ASSERT(PR_GetCurrentThread() == gSocketThread);
-
-  if (!aStream->CountAsActive()) {
-    return;
-  }
-
-  MOZ_ASSERT(mConcurrent);
-  aStream->SetCountAsActive(false);
-  --mConcurrent;
-
-  LOG3(("DecrementConcurrent %p id=0x%X concurrent=%d\n",
-        this, aStream->StreamID(), mConcurrent));
-
-  ProcessPending();
-}
-
-void
-SpdySession31::zlibInit()
-{
-  mDownstreamZlib.zalloc = SpdyZlibReporter::Alloc;
-  mDownstreamZlib.zfree = SpdyZlibReporter::Free;
-  mDownstreamZlib.opaque = Z_NULL;
-
-  inflateInit(&mDownstreamZlib);
-
-  mUpstreamZlib.zalloc = SpdyZlibReporter::Alloc;
-  mUpstreamZlib.zfree = SpdyZlibReporter::Free;
-  mUpstreamZlib.opaque = Z_NULL;
-
-  // mixing carte blanche compression with tls subjects us to traffic
-  // analysis attacks
-  deflateInit(&mUpstreamZlib, Z_NO_COMPRESSION);
-  deflateSetDictionary(&mUpstreamZlib,
-                       SpdyStream31::kDictionary,
-                       sizeof(SpdyStream31::kDictionary));
-}
-
-// Need to decompress some data in order to keep the compression
-// context correct, but we really don't care what the result is
-nsresult
-SpdySession31::UncompressAndDiscard(uint32_t offset,
-                                    uint32_t blockLen)
-{
-  char *blockStart = &mInputFrameBuffer[offset];
-  unsigned char trash[2048];
-  mDownstreamZlib.avail_in = blockLen;
-  mDownstreamZlib.next_in = reinterpret_cast<unsigned char *>(blockStart);
-  bool triedDictionary = false;
-
-  do {
-    mDownstreamZlib.next_out = trash;
-    mDownstreamZlib.avail_out = sizeof(trash);
-    int zlib_rv = inflate(&mDownstreamZlib, Z_NO_FLUSH);
-
-    if (zlib_rv == Z_NEED_DICT) {
-      if (triedDictionary) {
-        LOG3(("SpdySession31::UncompressAndDiscard %p Dictionary Error\n", this));
-        return NS_ERROR_ILLEGAL_VALUE;
-      }
-
-      triedDictionary = true;
-      inflateSetDictionary(&mDownstreamZlib, SpdyStream31::kDictionary,
-                           sizeof(SpdyStream31::kDictionary));
-    }
-
-    if (zlib_rv == Z_DATA_ERROR)
-      return NS_ERROR_ILLEGAL_VALUE;
-
-    if (zlib_rv == Z_MEM_ERROR)
-      return NS_ERROR_FAILURE;
-  }
-  while (mDownstreamZlib.avail_in);
-  return NS_OK;
-}
-
-void
-SpdySession31::GeneratePing(uint32_t aID)
-{
-  MOZ_ASSERT(PR_GetCurrentThread() == gSocketThread);
-  LOG3(("SpdySession31::GeneratePing %p 0x%X\n", this, aID));
-
-  EnsureBuffer(mOutputQueueBuffer, mOutputQueueUsed + 12,
-               mOutputQueueUsed, mOutputQueueSize);
-  char *packet = mOutputQueueBuffer.get() + mOutputQueueUsed;
-  mOutputQueueUsed += 12;
-
-  packet[0] = kFlag_Control;
-  packet[1] = kVersion;
-  packet[2] = 0;
-  packet[3] = CONTROL_TYPE_PING;
-  packet[4] = 0;                                  /* flags */
-  packet[5] = 0;
-  packet[6] = 0;
-  packet[7] = 4;                                  /* length */
-
-  aID = PR_htonl(aID);
-  memcpy(packet + 8, &aID, 4);
-
-  LogIO(this, nullptr, "Generate Ping", packet, 12);
-  FlushOutputQueue();
-}
-
-void
-SpdySession31::GenerateRstStream(uint32_t aStatusCode, uint32_t aID)
-{
-  MOZ_ASSERT(PR_GetCurrentThread() == gSocketThread);
-  LOG3(("SpdySession31::GenerateRst %p 0x%X %d\n", this, aID, aStatusCode));
-
-  EnsureBuffer(mOutputQueueBuffer, mOutputQueueUsed + 16,
-               mOutputQueueUsed, mOutputQueueSize);
-  char *packet = mOutputQueueBuffer.get() + mOutputQueueUsed;
-  mOutputQueueUsed += 16;
-
-  packet[0] = kFlag_Control;
-  packet[1] = kVersion;
-  packet[2] = 0;
-  packet[3] = CONTROL_TYPE_RST_STREAM;
-  packet[4] = 0;                                  /* flags */
-  packet[5] = 0;
-  packet[6] = 0;
-  packet[7] = 8;                                  /* length */
-
-  aID = PR_htonl(aID);
-  memcpy(packet + 8, &aID, 4);
-  aStatusCode = PR_htonl(aStatusCode);
-  memcpy(packet + 12, &aStatusCode, 4);
-
-  LogIO(this, nullptr, "Generate Reset", packet, 16);
-  FlushOutputQueue();
-}
-
-void
-SpdySession31::GenerateGoAway(uint32_t aStatusCode)
-{
-  MOZ_ASSERT(PR_GetCurrentThread() == gSocketThread);
-  LOG3(("SpdySession31::GenerateGoAway %p code=%X\n", this, aStatusCode));
-
-  EnsureBuffer(mOutputQueueBuffer, mOutputQueueUsed + 16,
-               mOutputQueueUsed, mOutputQueueSize);
-  char *packet = mOutputQueueBuffer.get() + mOutputQueueUsed;
-  mOutputQueueUsed += 16;
-
-  memset(packet, 0, 16);
-  packet[0] = kFlag_Control;
-  packet[1] = kVersion;
-  packet[3] = CONTROL_TYPE_GOAWAY;
-  packet[7] = 8;                                  /* data length */
-
-  // last-good-stream-id are bytes 8-11, when we accept server push this will
-  // need to be set non zero
-
-  // bytes 12-15 are the status code.
-  aStatusCode = PR_htonl(aStatusCode);
-  memcpy(packet + 12, &aStatusCode, 4);
-
-  LogIO(this, nullptr, "Generate GoAway", packet, 16);
-  FlushOutputQueue();
-}
-
-void
-SpdySession31::GenerateSettings()
-{
-  uint32_t sessionWindowBump = ASpdySession::kInitialRwin - kDefaultRwin;
-  MOZ_ASSERT(PR_GetCurrentThread() == gSocketThread);
-  LOG3(("SpdySession31::GenerateSettings %p\n", this));
-
-// sized for 3 settings and a session window update to follow
-  static const uint32_t maxDataLen = 4 + 3 * 8 + 16;
-  EnsureBuffer(mOutputQueueBuffer, mOutputQueueUsed + 8 + maxDataLen,
-               mOutputQueueUsed, mOutputQueueSize);
-  char *packet = mOutputQueueBuffer.get() + mOutputQueueUsed;
-
-  memset(packet, 0, 8 + maxDataLen);
-  packet[0] = kFlag_Control;
-  packet[1] = kVersion;
-  packet[3] = CONTROL_TYPE_SETTINGS;
-
-  uint8_t numberOfEntries = 0;
-
-  // entries need to be listed in order by ID
-  // 1st entry is bytes 12 to 19
-  // 2nd entry is bytes 20 to 27
-  // 3rd entry is bytes 28 to 35
-
-  if (!gHttpHandler->AllowPush()) {
-    // announcing that we accept 0 incoming streams is done to
-    // disable server push
-    packet[15 + 8 * numberOfEntries] = SETTINGS_TYPE_MAX_CONCURRENT;
-    // The value portion of the setting pair is already initialized to 0
-    numberOfEntries++;
-  }
-
-  // Advertise the Push RWIN and on each client SYN_STREAM pipeline
-  // a window update with it in order to use larger initial windows with pulled
-  // streams.
-  packet[15 + 8 * numberOfEntries] = SETTINGS_TYPE_INITIAL_WINDOW;
-  uint32_t rwin = PR_htonl(mPushAllowance);
-  memcpy(packet + 16 + 8 * numberOfEntries, &rwin, 4);
-  numberOfEntries++;
-
-  uint32_t dataLen = 4 + 8 * numberOfEntries;
-  mOutputQueueUsed += 8 + dataLen;
-  packet[7] = dataLen;
-  packet[11] = numberOfEntries;
-
-  LogIO(this, nullptr, "Generate Settings", packet, 8 + dataLen);
-
-  if (kDefaultRwin >= ASpdySession::kInitialRwin)
-    goto generateSettings_complete;
-
-  // send a window update for the session (Stream 0) for something large
-  sessionWindowBump = PR_htonl(sessionWindowBump);
-  mLocalSessionWindow = ASpdySession::kInitialRwin;
-
-  packet = mOutputQueueBuffer.get() + mOutputQueueUsed;
-  mOutputQueueUsed += 16;
-
-  packet[0] = kFlag_Control;
-  packet[1] = kVersion;
-  packet[3] = CONTROL_TYPE_WINDOW_UPDATE;
-  packet[7] = 8; // 8 data bytes after 8 byte header
-
-  // 8 to 11 stay 0 bytes for id = 0
-  memcpy(packet + 12, &sessionWindowBump, 4);
-
-  LOG3(("Session Window increase at start of session %p %u\n",
-        this, PR_ntohl(sessionWindowBump)));
-  LogIO(this, nullptr, "Session Window Bump ", packet, 16);
-
-generateSettings_complete:
-  FlushOutputQueue();
-}
-
-// perform a bunch of integrity checks on the stream.
-// returns true if passed, false (plus LOG and ABORT) if failed.
-bool
-SpdySession31::VerifyStream(SpdyStream31 *aStream, uint32_t aOptionalID = 0)
-{
-  // This is annoying, but at least it is O(1)
-  MOZ_ASSERT(PR_GetCurrentThread() == gSocketThread);
-
-#ifndef DEBUG
-  // Only do the real verification in debug builds
-  return true;
-#endif
-
-  if (!aStream)
-    return true;
-
-  uint32_t test = 0;
-
-  do {
-    if (aStream->StreamID() == kDeadStreamID)
-      break;
-
-    nsAHttpTransaction *trans = aStream->Transaction();
-
-    test++;
-    if (!trans)
-      break;
-
-    test++;
-    if (mStreamTransactionHash.Get(trans) != aStream)
-      break;
-
-    if (aStream->StreamID()) {
-      SpdyStream31 *idStream = mStreamIDHash.Get(aStream->StreamID());
-
-      test++;
-      if (idStream != aStream)
-        break;
-
-      if (aOptionalID) {
-        test++;
-        if (idStream->StreamID() != aOptionalID)
-          break;
-      }
-    }
-
-    // tests passed
-    return true;
-  } while (0);
-
-  LOG(("SpdySession31 %p VerifyStream Failure %p stream->id=0x%X "
-       "optionalID=0x%X trans=%p test=%d\n",
-       this, aStream, aStream->StreamID(),
-       aOptionalID, aStream->Transaction(), test));
-
-  MOZ_ASSERT(false, "VerifyStream");
-  return false;
-}
-
-void
-SpdySession31::CleanupStream(SpdyStream31 *aStream, nsresult aResult,
-                             rstReason aResetCode)
-{
-  MOZ_ASSERT(PR_GetCurrentThread() == gSocketThread);
-  LOG3(("SpdySession31::CleanupStream %p %p 0x%X %X\n",
-        this, aStream, aStream ? aStream->StreamID() : 0, aResult));
-  if (!aStream) {
-    return;
-  }
-
-  SpdyPushedStream31 *pushSource = nullptr;
-
-  if (NS_SUCCEEDED(aResult) && aStream->DeferCleanupOnSuccess()) {
-    LOG(("SpdySession31::CleanupStream 0x%X deferred\n", aStream->StreamID()));
-    return;
-  }
-
-  if (!VerifyStream(aStream)) {
-    LOG(("SpdySession31::CleanupStream failed to verify stream\n"));
-    return;
-  }
-
-  pushSource = aStream->PushSource();
-
-  if (!aStream->RecvdFin() && aStream->StreamID()) {
-    LOG3(("Stream had not processed recv FIN, sending RST code %X\n",
-          aResetCode));
-    GenerateRstStream(aResetCode, aStream->StreamID());
-    DecrementConcurrent(aStream);
-  }
-
-  CloseStream(aStream, aResult);
-
-  // Remove the stream from the ID hash table and, if an even id, the pushed
-  // table too.
-  uint32_t id = aStream->StreamID();
-  if (id > 0) {
-    mStreamIDHash.Remove(id);
-    if (!(id & 1))
-      mPushedStreams.RemoveElement(aStream);
-  }
-
-  RemoveStreamFromQueues(aStream);
-
-  // removing from the stream transaction hash will
-  // delete the SpdyStream31 and drop the reference to
-  // its transaction
-  mStreamTransactionHash.Remove(aStream->Transaction());
-
-  if (mShouldGoAway && !mStreamTransactionHash.Count())
-    Close(NS_OK);
-
-  if (pushSource) {
-    pushSource->SetDeferCleanupOnSuccess(false);
-    CleanupStream(pushSource, aResult, aResetCode);
-  }
-}
-
-static void RemoveStreamFromQueue(SpdyStream31 *aStream, nsDeque &queue)
-{
-  size_t size = queue.GetSize();
-  for (size_t count = 0; count < size; ++count) {
-    SpdyStream31 *stream = static_cast<SpdyStream31 *>(queue.PopFront());
-    if (stream != aStream)
-      queue.Push(stream);
-  }
-}
-
-void
-SpdySession31::RemoveStreamFromQueues(SpdyStream31 *aStream)
-{
-  RemoveStreamFromQueue(aStream, mReadyForWrite);
-  RemoveStreamFromQueue(aStream, mQueuedStreams);
-  RemoveStreamFromQueue(aStream, mReadyForRead);
-}
-
-void
-SpdySession31::CloseStream(SpdyStream31 *aStream, nsresult aResult)
-{
-  MOZ_ASSERT(PR_GetCurrentThread() == gSocketThread);
-  LOG3(("SpdySession31::CloseStream %p %p 0x%x %X\n",
-        this, aStream, aStream->StreamID(), aResult));
-
-  // Check if partial frame reader
-  if (aStream == mInputFrameDataStream) {
-    LOG3(("Stream had active partial read frame on close"));
-    ChangeDownstreamState(DISCARDING_DATA_FRAME);
-    mInputFrameDataStream = nullptr;
-  }
-
-  RemoveStreamFromQueues(aStream);
-
-  if (aStream->IsTunnel()) {
-    UnRegisterTunnel(aStream);
-  }
-
-  // Send the stream the close() indication
-  aStream->Close(aResult);
-}
-
-nsresult
-SpdySession31::HandleSynStream(SpdySession31 *self)
-{
-  MOZ_ASSERT(self->mFrameControlType == CONTROL_TYPE_SYN_STREAM);
-
-  if (self->mInputFrameDataSize < 18) {
-    LOG3(("SpdySession31::HandleSynStream %p SYN_STREAM too short data=%d",
-          self, self->mInputFrameDataSize));
-    return NS_ERROR_ILLEGAL_VALUE;
-  }
-
-  uint32_t streamID =
-    PR_ntohl(reinterpret_cast<uint32_t *>(self->mInputFrameBuffer.get())[2]);
-  uint32_t associatedID =
-    PR_ntohl(reinterpret_cast<uint32_t *>(self->mInputFrameBuffer.get())[3]);
-  uint8_t flags = reinterpret_cast<uint8_t *>(self->mInputFrameBuffer.get())[4];
-
-  LOG3(("SpdySession31::HandleSynStream %p recv SYN_STREAM (push) "
-        "for ID 0x%X associated with 0x%X.\n",
-        self, streamID, associatedID));
-
-  if (streamID & 0x01) {                   // test for odd stream ID
-    LOG3(("SpdySession31::HandleSynStream %p recvd SYN_STREAM id must be even.",
-          self));
-    return NS_ERROR_ILLEGAL_VALUE;
-  }
-
-  // confirm associated-to
-  nsresult rv = self->SetInputFrameDataStream(associatedID);
-  if (NS_FAILED(rv))
-    return rv;
-  SpdyStream31 *associatedStream = self->mInputFrameDataStream;
-
-  ++(self->mServerPushedResources);
-
-  // Anytime we start using the high bit of stream ID (either client or server)
-  // begin to migrate to a new session.
-  if (streamID >= kMaxStreamID)
-    self->mShouldGoAway = true;
-
-  bool resetStream = true;
-  SpdyPushCache *cache = nullptr;
-
-  if (!(flags & kFlag_Data_UNI)) {
-    // pushed streams require UNIDIRECTIONAL flag
-    LOG3(("SpdySession31::HandleSynStream %p ID %0x%X associated ID 0x%X failed.\n",
-          self, streamID, associatedID));
-    self->GenerateRstStream(RST_PROTOCOL_ERROR, streamID);
-
-  } else if (!associatedID) {
-    // associated stream 0 will never find a match, but the spec requires a
-    // PROTOCOL_ERROR in this specific case
-    LOG3(("SpdySession31::HandleSynStream %p associated ID of 0 failed.\n", self));
-    self->GenerateRstStream(RST_PROTOCOL_ERROR, streamID);
-
-  } else if (!gHttpHandler->AllowPush()) {
-    // MAX_CONCURRENT_STREAMS of 0 in settings should have disabled push,
-    // but some servers are buggy about that.. or the config could have
-    // been updated after the settings frame was sent. In both cases just
-    // reject the pushed stream as refused
-    LOG3(("SpdySession31::HandleSynStream Push Recevied when Disabled\n"));
-    self->GenerateRstStream(RST_REFUSED_STREAM, streamID);
-
-  } else if (!associatedStream) {
-    LOG3(("SpdySession31::HandleSynStream %p lookup associated ID failed.\n", self));
-    self->GenerateRstStream(RST_INVALID_STREAM, streamID);
-
-  } else {
-    nsIRequestContext *requestContext = associatedStream->RequestContext();
-    if (requestContext) {
-      requestContext->GetSpdyPushCache(&cache);
-      if (!cache) {
-        cache = new SpdyPushCache();
-        if (!cache || NS_FAILED(requestContext->SetSpdyPushCache(cache))) {
-          delete cache;
-          cache = nullptr;
-        }
-      }
-    }
-    if (!cache) {
-      // this is unexpected, but we can handle it just be refusing the push
-      LOG3(("SpdySession31::HandleSynStream Push Recevied without push cache\n"));
-      self->GenerateRstStream(RST_REFUSED_STREAM, streamID);
-    }
-    else {
-      resetStream = false;
-    }
-  }
-
-  if (resetStream) {
-    // Need to decompress the headers even though we aren't using them yet in
-    // order to keep the compression context consistent for other syn_reply frames
-    rv = self->UncompressAndDiscard(18, self->mInputFrameDataSize - 10);
-    if (NS_FAILED(rv)) {
-      LOG(("SpdySession31::HandleSynStream uncompress failed\n"));
-      return rv;
-    }
-    self->ResetDownstreamState();
-    return NS_OK;
-  }
-
-  // Create the buffering transaction and push stream
-  RefPtr<SpdyPush31TransactionBuffer> transactionBuffer =
-    new SpdyPush31TransactionBuffer();
-  transactionBuffer->SetConnection(self);
-  SpdyPushedStream31 *pushedStream =
-    new SpdyPushedStream31(transactionBuffer, self,
-                           associatedStream, streamID);
-
-  // ownership of the pushed stream is by the transaction hash, just as it
-  // is for a client initiated stream. Errors that aren't fatal to the
-  // whole session must call cleanupStream() after this point in order
-  // to remove the stream from that hash.
-  self->mStreamTransactionHash.Put(transactionBuffer, pushedStream);
-  self->mPushedStreams.AppendElement(pushedStream);
-
-  // The pushed stream is unidirectional so it is fully open immediately
-  rv = pushedStream->SetFullyOpen();
-  if (NS_FAILED(rv)) {
-    LOG(("SpdySession31::HandleSynStream pushedstream fully open failed\n"));
-    self->CleanupStream(pushedStream, rv, RST_CANCEL);
-    self->ResetDownstreamState();
-    return NS_OK;
-  }
-
-  // Uncompress the response headers into a stream specific buffer, leaving them
-  // in spdy format for the time being.
-  rv = pushedStream->Uncompress(&self->mDownstreamZlib,
-                                &self->mInputFrameBuffer[18],
-                                self->mInputFrameDataSize - 10);
-  if (NS_FAILED(rv)) {
-    LOG(("SpdySession31::HandleSynStream uncompress failed\n"));
-    return rv;
-  }
-
-  if (self->RegisterStreamID(pushedStream, streamID) == kDeadStreamID) {
-    LOG(("SpdySession31::HandleSynStream registerstreamid failed\n"));
-    return NS_ERROR_FAILURE;
-  }
-
-  // Fake the request side of the pushed HTTP transaction. Sets up hash
-  // key and origin
-  uint32_t notUsed;
-  pushedStream->ReadSegments(nullptr, 1, &notUsed);
-
-  nsAutoCString key;
-  if (!pushedStream->GetHashKey(key)) {
-    LOG(("SpdySession31::HandleSynStream one of :host :scheme :path missing from push\n"));
-    self->CleanupStream(pushedStream, NS_ERROR_FAILURE, RST_INVALID_STREAM);
-    self->ResetDownstreamState();
-    return NS_OK;
-  }
-
-  if (!associatedStream->Origin().Equals(pushedStream->Origin())) {
-    LOG(("SpdySession31::HandleSynStream pushed stream mismatched origin\n"));
-    self->CleanupStream(pushedStream, NS_ERROR_FAILURE, RST_INVALID_STREAM);
-    self->ResetDownstreamState();
-    return NS_OK;
-  }
-
-  if (!cache->RegisterPushedStreamSpdy31(key, pushedStream)) {
-    LOG(("SpdySession31::HandleSynStream registerPushedStream Failed\n"));
-    self->CleanupStream(pushedStream, NS_ERROR_FAILURE, RST_INVALID_STREAM);
-    self->ResetDownstreamState();
-    return NS_OK;
-  }
-
-  self->ResetDownstreamState();
-  return NS_OK;
-}
-
-nsresult
-SpdySession31::SetInputFrameDataStream(uint32_t streamID)
-{
-  mInputFrameDataStream = mStreamIDHash.Get(streamID);
-  if (VerifyStream(mInputFrameDataStream, streamID))
-    return NS_OK;
-
-  LOG(("SpdySession31::SetInputFrameDataStream failed to verify 0x%X\n",
-       streamID));
-  mInputFrameDataStream = nullptr;
-  return NS_ERROR_UNEXPECTED;
-}
-
-nsresult
-SpdySession31::HandleSynReply(SpdySession31 *self)
-{
-  MOZ_ASSERT(self->mFrameControlType == CONTROL_TYPE_SYN_REPLY);
-
-  if (self->mInputFrameDataSize < 4) {
-    LOG3(("SpdySession31::HandleSynReply %p SYN REPLY too short data=%d",
-          self, self->mInputFrameDataSize));
-    // A framing error is a session wide error that cannot be recovered
-    return NS_ERROR_ILLEGAL_VALUE;
-  }
-
-  uint32_t streamID =
-    PR_ntohl(reinterpret_cast<uint32_t *>(self->mInputFrameBuffer.get())[2]);
-  LOG3(("SpdySession31::HandleSynReply %p lookup via streamID 0x%X in syn_reply.\n",
-        self, streamID));
-  nsresult rv = self->SetInputFrameDataStream(streamID);
-  if (NS_FAILED(rv))
-    return rv;
-
-  if (!self->mInputFrameDataStream) {
-    // Cannot find stream. We can continue the SPDY session, but we need to
-    // uncompress the header block to maintain the correct compression context
-
-    LOG3(("SpdySession31::HandleSynReply %p lookup streamID in syn_reply "
-          "0x%X failed. NextStreamID = 0x%X\n",
-          self, streamID, self->mNextStreamID));
-
-    if (streamID >= self->mNextStreamID)
-      self->GenerateRstStream(RST_INVALID_STREAM, streamID);
-
-    rv = self->UncompressAndDiscard(12, self->mInputFrameDataSize - 4);
-    if (NS_FAILED(rv)) {
-      LOG(("SpdySession31::HandleSynReply uncompress failed\n"));
-      // this is fatal to the session
-      return rv;
-    }
-
-    self->ResetDownstreamState();
-    return NS_OK;
-  }
-
-  // Uncompress the headers into a stream specific buffer, leaving them in
-  // spdy format for the time being. Make certain to do this
-  // step before any error handling that might abort the stream but not
-  // the session becuase the session compression context will become
-  // inconsistent if all of the compressed data is not processed.
-  rv = self->mInputFrameDataStream->Uncompress(&self->mDownstreamZlib,
-                                               &self->mInputFrameBuffer[12],
-                                               self->mInputFrameDataSize - 4);
-
-  if (NS_FAILED(rv)) {
-    LOG(("SpdySession31::HandleSynReply uncompress failed\n"));
-    return rv;
-  }
-
-  if (self->mInputFrameDataStream->GetFullyOpen()) {
-    // "If an endpoint receives multiple SYN_REPLY frames for the same active
-    // stream ID, it MUST issue a stream error (Section 2.4.2) with the error
-    // code STREAM_IN_USE."
-    //
-    // "STREAM_ALREADY_CLOSED. The endpoint received a data or SYN_REPLY
-    // frame for a stream which is half closed."
-    //
-    // If the stream is open then just RST_STREAM with STREAM_IN_USE
-    // If the stream is half closed then RST_STREAM with STREAM_ALREADY_CLOSED
-    // abort the session
-    //
-    LOG3(("SpdySession31::HandleSynReply %p dup SYN_REPLY for 0x%X"
-          " recvdfin=%d", self, self->mInputFrameDataStream->StreamID(),
-          self->mInputFrameDataStream->RecvdFin()));
-
-    self->CleanupStream(self->mInputFrameDataStream, NS_ERROR_ALREADY_OPENED,
-                        self->mInputFrameDataStream->RecvdFin() ?
-                        RST_STREAM_ALREADY_CLOSED : RST_STREAM_IN_USE);
-    self->ResetDownstreamState();
-    return NS_OK;
-  }
-
-  rv = self->mInputFrameDataStream->SetFullyOpen();
-  if (NS_FAILED(rv)) {
-    LOG(("SpdySession31::HandleSynReply SetFullyOpen failed\n"));
-    if (self->mInputFrameDataStream->IsTunnel()) {
-      gHttpHandler->ConnMgr()->CancelTransactions(
-        self->mInputFrameDataStream->Transaction()->ConnectionInfo(),
-        NS_ERROR_CONNECTION_REFUSED);
-    }
-    self->CleanupStream(self->mInputFrameDataStream, rv, RST_CANCEL);
-    self->ResetDownstreamState();
-    return NS_OK;
-  }
-
-  self->mInputFrameDataLast = self->mInputFrameBuffer[4] & kFlag_Data_FIN;
-  self->mInputFrameDataStream->UpdateTransportReadEvents(self->mInputFrameDataSize);
-  self->mLastDataReadEpoch = self->mLastReadEpoch;
-
-  if (self->mInputFrameBuffer[4] & ~kFlag_Data_FIN) {
-    LOG3(("SynReply %p had undefined flag set 0x%X\n", self, streamID));
-    self->CleanupStream(self->mInputFrameDataStream, NS_ERROR_ILLEGAL_VALUE,
-                        RST_PROTOCOL_ERROR);
-    self->ResetDownstreamState();
-    return NS_OK;
-  }
-
-  if (!self->mInputFrameDataLast) {
-    // don't process the headers yet as there could be more coming from HEADERS
-    // frames
-    self->ResetDownstreamState();
-    return NS_OK;
-  }
-
-  rv = self->ResponseHeadersComplete();
-  if (rv == NS_ERROR_ILLEGAL_VALUE) {
-    LOG3(("SpdySession31::HandleSynReply %p PROTOCOL_ERROR detected 0x%X\n",
-          self, streamID));
-    self->CleanupStream(self->mInputFrameDataStream, rv, RST_PROTOCOL_ERROR);
-    self->ResetDownstreamState();
-    rv = NS_OK;
-  }
-  return rv;
-}
-
-// ResponseHeadersComplete() returns NS_ERROR_ILLEGAL_VALUE when the stream
-// should be reset with a PROTOCOL_ERROR, NS_OK when the SYN_REPLY was
-// fine, and any other error is fatal to the session.
-nsresult
-SpdySession31::ResponseHeadersComplete()
-{
-  LOG3(("SpdySession31::ResponseHeadersComplete %p for 0x%X fin=%d",
-        this, mInputFrameDataStream->StreamID(), mInputFrameDataLast));
-
-  // The spdystream needs to see flattened http headers
-  // Uncompressed spdy format headers currently live in
-  // SpdyStream31::mDecompressBuffer - convert that to HTTP format in
-  // mFlatHTTPResponseHeaders via ConvertHeaders()
-
-  mFlatHTTPResponseHeadersOut = 0;
-  nsresult rv = mInputFrameDataStream->ConvertHeaders(mFlatHTTPResponseHeaders);
-  if (NS_FAILED(rv))
-    return rv;
-
-  ChangeDownstreamState(PROCESSING_COMPLETE_HEADERS);
-  return NS_OK;
-}
-
-nsresult
-SpdySession31::HandleRstStream(SpdySession31 *self)
-{
-  MOZ_ASSERT(self->mFrameControlType == CONTROL_TYPE_RST_STREAM);
-
-  if (self->mInputFrameDataSize != 8) {
-    LOG3(("SpdySession31::HandleRstStream %p RST_STREAM wrong length data=%d",
-          self, self->mInputFrameDataSize));
-    return NS_ERROR_ILLEGAL_VALUE;
-  }
-
-  uint8_t flags = reinterpret_cast<uint8_t *>(self->mInputFrameBuffer.get())[4];
-
-  uint32_t streamID =
-    PR_ntohl(reinterpret_cast<uint32_t *>(self->mInputFrameBuffer.get())[2]);
-
-  self->mDownstreamRstReason =
-    PR_ntohl(reinterpret_cast<uint32_t *>(self->mInputFrameBuffer.get())[3]);
-
-  LOG3(("SpdySession31::HandleRstStream %p RST_STREAM Reason Code %u ID %x "
-        "flags %x", self, self->mDownstreamRstReason, streamID, flags));
-
-  if (flags != 0) {
-    LOG3(("SpdySession31::HandleRstStream %p RST_STREAM with flags is illegal",
-          self));
-    return NS_ERROR_ILLEGAL_VALUE;
-  }
-
-  if (self->mDownstreamRstReason == RST_INVALID_STREAM ||
-      self->mDownstreamRstReason == RST_STREAM_IN_USE ||
-      self->mDownstreamRstReason == RST_FLOW_CONTROL_ERROR) {
-    // basically just ignore this
-    LOG3(("SpdySession31::HandleRstStream %p No Reset Processing Needed.\n"));
-    self->ResetDownstreamState();
-    return NS_OK;
-  }
-
-  nsresult rv = self->SetInputFrameDataStream(streamID);
-
-  if (!self->mInputFrameDataStream) {
-    if (NS_FAILED(rv))
-      LOG(("SpdySession31::HandleRstStream %p lookup streamID for RST Frame "
-           "0x%X failed reason = %d :: VerifyStream Failed\n", self, streamID,
-           self->mDownstreamRstReason));
-
-    LOG3(("SpdySession31::HandleRstStream %p lookup streamID for RST Frame "
-          "0x%X failed reason = %d", self, streamID,
-          self->mDownstreamRstReason));
-    return NS_ERROR_ILLEGAL_VALUE;
-  }
-
-  self->ChangeDownstreamState(PROCESSING_CONTROL_RST_STREAM);
-  return NS_OK;
-}
-
-nsresult
-SpdySession31::HandleSettings(SpdySession31 *self)
-{
-  MOZ_ASSERT(self->mFrameControlType == CONTROL_TYPE_SETTINGS);
-
-  if (self->mInputFrameDataSize < 4) {
-    LOG3(("SpdySession31::HandleSettings %p SETTINGS wrong length data=%d",
-          self, self->mInputFrameDataSize));
-    return NS_ERROR_ILLEGAL_VALUE;
-  }
-
-  uint32_t numEntries =
-    PR_ntohl(reinterpret_cast<uint32_t *>(self->mInputFrameBuffer.get())[2]);
-
-  // Ensure frame is large enough for supplied number of entries
-  // Each entry is 8 bytes, frame data is reduced by 4 to account for
-  // the NumEntries value.
-  if ((self->mInputFrameDataSize - 4) < (numEntries * 8)) {
-    LOG3(("SpdySession31::HandleSettings %p SETTINGS wrong length data=%d",
-          self, self->mInputFrameDataSize));
-    return NS_ERROR_ILLEGAL_VALUE;
-  }
-
-  LOG3(("SpdySession31::HandleSettings %p SETTINGS Control Frame with %d entries",
-        self, numEntries));
-
-  for (uint32_t index = 0; index < numEntries; ++index) {
-    unsigned char *setting = reinterpret_cast<unsigned char *>
-      (self->mInputFrameBuffer.get()) + 12 + index * 8;
-
-    uint32_t flags = setting[0];
-    uint32_t id = PR_ntohl(reinterpret_cast<uint32_t *>(setting)[0]) & 0xffffff;
-    uint32_t value =  PR_ntohl(reinterpret_cast<uint32_t *>(setting)[1]);
-
-    LOG3(("Settings ID %d, Flags %X, Value %d", id, flags, value));
-
-    switch (id)
-    {
-    case SETTINGS_TYPE_MAX_CONCURRENT:
-      self->mMaxConcurrent = value;
-      self->ProcessPending();
-      break;
-
-    case SETTINGS_TYPE_INITIAL_WINDOW:
-      {
-        int32_t delta = value - self->mServerInitialStreamWindow;
-        self->mServerInitialStreamWindow = value;
-
-        // do not use SETTINGS to adjust the session window.
-
-        // we need to add the delta to all open streams (delta can be negative)
-        for (auto iter = self->mStreamTransactionHash.Iter();
-             !iter.Done();
-             iter.Next()) {
-          iter.Data()->UpdateRemoteWindow(delta);
-        }
-      }
-      break;
-
-    default:
-      break;
-    }
-
-  }
-
-  self->ResetDownstreamState();
-  return NS_OK;
-}
-
-nsresult
-SpdySession31::HandleNoop(SpdySession31 *self)
-{
-  MOZ_ASSERT(self->mFrameControlType == CONTROL_TYPE_NOOP);
-
-  // Should not be receiving noop frames in spdy/3.1, so we'll just
-  // make a log and ignore it
-
-  LOG3(("SpdySession31::HandleNoop %p NOP.", self));
-
-  self->ResetDownstreamState();
-  return NS_OK;
-}
-
-nsresult
-SpdySession31::HandlePing(SpdySession31 *self)
-{
-  MOZ_ASSERT(self->mFrameControlType == CONTROL_TYPE_PING);
-
-  if (self->mInputFrameDataSize != 4) {
-    LOG3(("SpdySession31::HandlePing %p PING had wrong amount of data %d",
-          self, self->mInputFrameDataSize));
-    return NS_ERROR_ILLEGAL_VALUE;
-  }
-
-  uint32_t pingID =
-    PR_ntohl(reinterpret_cast<uint32_t *>(self->mInputFrameBuffer.get())[2]);
-
-  LOG3(("SpdySession31::HandlePing %p PING ID 0x%X.", self, pingID));
-
-  if (pingID & 0x01) {
-    // presumably a reply to our timeout ping
-    self->mPingSentEpoch = 0;
-  }
-  else {
-    // Servers initiate even numbered pings, go ahead and echo it back
-    self->GeneratePing(pingID);
-  }
-
-  self->ResetDownstreamState();
-  return NS_OK;
-}
-
-nsresult
-SpdySession31::HandleGoAway(SpdySession31 *self)
-{
-  MOZ_ASSERT(self->mFrameControlType == CONTROL_TYPE_GOAWAY);
-
-  if (self->mInputFrameDataSize != 8) {
-    LOG3(("SpdySession31::HandleGoAway %p GOAWAY had wrong amount of data %d",
-          self, self->mInputFrameDataSize));
-    return NS_ERROR_ILLEGAL_VALUE;
-  }
-
-  self->mShouldGoAway = true;
-  self->mGoAwayID =
-    PR_ntohl(reinterpret_cast<uint32_t *>(self->mInputFrameBuffer.get())[2]);
-  self->mCleanShutdown = true;
-
-  // Find streams greater than the last-good ID and mark them for deletion
-  // in the mGoAwayStreamsToRestart queue. The underlying transaction can be
-  // restarted.
-  for (auto iter = self->mStreamTransactionHash.Iter();
-       !iter.Done();
-       iter.Next()) {
-
-    // These streams were not processed by the server and can be restarted. Do
-    // that after the enumerator completes to avoid the risk of a restart event
-    // re-entrantly modifying this hash. Be sure not to restart a pushed (even
-    // numbered) stream.
-    nsAutoPtr<SpdyStream31>& stream = iter.Data();
-    if ((stream->StreamID() > self->mGoAwayID && (stream->StreamID() & 1)) ||
-        !stream->HasRegisteredID()) {
-      self->mGoAwayStreamsToRestart.Push(stream);
-    }
-  }
-
-  // Process the streams marked for deletion and restart.
-  size_t size = self->mGoAwayStreamsToRestart.GetSize();
-  for (size_t count = 0; count < size; ++count) {
-    SpdyStream31 *stream =
-      static_cast<SpdyStream31 *>(self->mGoAwayStreamsToRestart.PopFront());
-
-    self->CloseStream(stream, NS_ERROR_NET_RESET);
-    if (stream->HasRegisteredID())
-      self->mStreamIDHash.Remove(stream->StreamID());
-    self->mStreamTransactionHash.Remove(stream->Transaction());
-  }
-
-  // Queued streams can also be deleted from this session and restarted
-  // in another one. (they were never sent on the network so they implicitly
-  // are not covered by the last-good id.
-  size = self->mQueuedStreams.GetSize();
-  for (size_t count = 0; count < size; ++count) {
-    SpdyStream31 *stream =
-      static_cast<SpdyStream31 *>(self->mQueuedStreams.PopFront());
-    MOZ_ASSERT(stream->Queued());
-    stream->SetQueued(false);
-    self->CloseStream(stream, NS_ERROR_NET_RESET);
-    self->mStreamTransactionHash.Remove(stream->Transaction());
-  }
-
-  LOG3(("SpdySession31::HandleGoAway %p GOAWAY Last-Good-ID 0x%X status 0x%X "
-        "live streams=%d\n", self, self->mGoAwayID,
-        PR_ntohl(reinterpret_cast<uint32_t *>(self->mInputFrameBuffer.get())[3]),
-        self->mStreamTransactionHash.Count()));
-
-  self->ResetDownstreamState();
-  return NS_OK;
-}
-
-nsresult
-SpdySession31::HandleHeaders(SpdySession31 *self)
-{
-  MOZ_ASSERT(self->mFrameControlType == CONTROL_TYPE_HEADERS);
-
-  if (self->mInputFrameDataSize < 4) {
-    LOG3(("SpdySession31::HandleHeaders %p HEADERS had wrong amount of data %d",
-          self, self->mInputFrameDataSize));
-    return NS_ERROR_ILLEGAL_VALUE;
-  }
-
-  uint32_t streamID =
-    PR_ntohl(reinterpret_cast<uint32_t *>(self->mInputFrameBuffer.get())[2]);
-  LOG3(("SpdySession31::HandleHeaders %p HEADERS for Stream 0x%X.\n",
-        self, streamID));
-  nsresult rv = self->SetInputFrameDataStream(streamID);
-  if (NS_FAILED(rv))
-    return rv;
-
-  if (!self->mInputFrameDataStream) {
-    LOG3(("SpdySession31::HandleHeaders %p lookup streamID 0x%X failed.\n",
-          self, streamID));
-    if (streamID >= self->mNextStreamID)
-      self->GenerateRstStream(RST_INVALID_STREAM, streamID);
-
-    rv = self->UncompressAndDiscard(12, self->mInputFrameDataSize - 4);
-    if (NS_FAILED(rv)) {
-      LOG(("SpdySession31::HandleHeaders uncompress failed\n"));
-      // this is fatal to the session
-      return rv;
-    }
-    self->ResetDownstreamState();
-    return NS_OK;
-  }
-
-  // Uncompress the headers into local buffers in the SpdyStream, leaving
-  // them in spdy format for the time being. Make certain to do this
-  // step before any error handling that might abort the stream but not
-  // the session becuase the session compression context will become
-  // inconsistent if all of the compressed data is not processed.
-  rv = self->mInputFrameDataStream->Uncompress(&self->mDownstreamZlib,
-                                               &self->mInputFrameBuffer[12],
-                                               self->mInputFrameDataSize - 4);
-  if (NS_FAILED(rv)) {
-    LOG(("SpdySession31::HandleHeaders uncompress failed\n"));
-    return rv;
-  }
-
-  self->mInputFrameDataLast = self->mInputFrameBuffer[4] & kFlag_Data_FIN;
-  self->mInputFrameDataStream->
-    UpdateTransportReadEvents(self->mInputFrameDataSize);
-  self->mLastDataReadEpoch = self->mLastReadEpoch;
-
-  if (self->mInputFrameBuffer[4] & ~kFlag_Data_FIN) {
-    LOG3(("Headers %p had undefined flag set 0x%X\n", self, streamID));
-    self->CleanupStream(self->mInputFrameDataStream, NS_ERROR_ILLEGAL_VALUE,
-                        RST_PROTOCOL_ERROR);
-    self->ResetDownstreamState();
-    return NS_OK;
-  }
-
-  if (!self->mInputFrameDataLast) {
-    // don't process the headers yet as there could be more HEADERS frames
-    self->ResetDownstreamState();
-    return NS_OK;
-  }
-
-  rv = self->ResponseHeadersComplete();
-  if (rv == NS_ERROR_ILLEGAL_VALUE) {
-    LOG3(("SpdySession31::HanndleHeaders %p PROTOCOL_ERROR detected 0x%X\n",
-          self, streamID));
-    self->CleanupStream(self->mInputFrameDataStream, rv, RST_PROTOCOL_ERROR);
-    self->ResetDownstreamState();
-    rv = NS_OK;
-  }
-  return rv;
-}
-
-nsresult
-SpdySession31::HandleWindowUpdate(SpdySession31 *self)
-{
-  MOZ_ASSERT(self->mFrameControlType == CONTROL_TYPE_WINDOW_UPDATE);
-
-  if (self->mInputFrameDataSize < 8) {
-    LOG3(("SpdySession31::HandleWindowUpdate %p Window Update wrong length %d\n",
-          self, self->mInputFrameDataSize));
-    return NS_ERROR_ILLEGAL_VALUE;
-  }
-
-  uint32_t delta =
-    PR_ntohl(reinterpret_cast<uint32_t *>(self->mInputFrameBuffer.get())[3]);
-  delta &= 0x7fffffff;
-  uint32_t streamID =
-    PR_ntohl(reinterpret_cast<uint32_t *>(self->mInputFrameBuffer.get())[2]);
-  streamID &= 0x7fffffff;
-
-  LOG3(("SpdySession31::HandleWindowUpdate %p len=%d for Stream 0x%X.\n",
-        self, delta, streamID));
-
-  // ID of 0 is a session window update
-  if (streamID) {
-    nsresult rv = self->SetInputFrameDataStream(streamID);
-    if (NS_FAILED(rv))
-      return rv;
-
-    if (!self->mInputFrameDataStream) {
-      LOG3(("SpdySession31::HandleWindowUpdate %p lookup streamID 0x%X failed.\n",
-            self, streamID));
-      if (streamID >= self->mNextStreamID)
-        self->GenerateRstStream(RST_INVALID_STREAM, streamID);
-      self->ResetDownstreamState();
-      return NS_OK;
-    }
-
-    self->mInputFrameDataStream->UpdateRemoteWindow(delta);
-  } else {
-    int64_t oldRemoteWindow = self->mRemoteSessionWindow;
-    self->mRemoteSessionWindow += delta;
-    if ((oldRemoteWindow <= 0) && (self->mRemoteSessionWindow > 0)) {
-      LOG3(("SpdySession31::HandleWindowUpdate %p restart session window\n",
-            self));
-      for (auto iter = self->mStreamTransactionHash.Iter();
-           !iter.Done();
-           iter.Next()) {
-        MOZ_ASSERT(self->mRemoteSessionWindow > 0);
-
-        nsAutoPtr<SpdyStream31>& stream = iter.Data();
-        if (!stream->BlockedOnRwin() || stream->RemoteWindow() <= 0) {
-          continue;
-        }
-
-        self->mReadyForWrite.Push(stream);
-        self->SetWriteCallbacks();
-      }
-    }
-  }
-
-  self->ResetDownstreamState();
-  return NS_OK;
-}
-
-nsresult
-SpdySession31::HandleCredential(SpdySession31 *self)
-{
-  MOZ_ASSERT(self->mFrameControlType == CONTROL_TYPE_CREDENTIAL);
-
-  // These aren't used yet. Just ignore the frame.
-
-  LOG3(("SpdySession31::HandleCredential %p NOP.", self));
-
-  self->ResetDownstreamState();
-  return NS_OK;
-}
-
-//-----------------------------------------------------------------------------
-// nsAHttpTransaction. It is expected that nsHttpConnection is the caller
-// of these methods
-//-----------------------------------------------------------------------------
-
-void
-SpdySession31::OnTransportStatus(nsITransport* aTransport,
-                                 nsresult aStatus,
-                                 int64_t aProgress)
-{
-  MOZ_ASSERT(PR_GetCurrentThread() == gSocketThread);
-
-  switch (aStatus) {
-    // These should appear only once, deliver to the first
-    // transaction on the session.
-  case NS_NET_STATUS_RESOLVING_HOST:
-  case NS_NET_STATUS_RESOLVED_HOST:
-  case NS_NET_STATUS_CONNECTING_TO:
-  case NS_NET_STATUS_CONNECTED_TO:
-  {
-    SpdyStream31 *target = mStreamIDHash.Get(1);
-    nsAHttpTransaction *transaction = target ? target->Transaction() : nullptr;
-    if (transaction)
-      transaction->OnTransportStatus(aTransport, aStatus, aProgress);
-    break;
-  }
-
-  default:
-    // The other transport events are ignored here because there is no good
-    // way to map them to the right transaction in spdy. Instead, the events
-    // are generated again from the spdy code and passed directly to the
-    // correct transaction.
-
-    // NS_NET_STATUS_SENDING_TO:
-    // This is generated by the socket transport when (part) of
-    // a transaction is written out
-    //
-    // There is no good way to map it to the right transaction in spdy,
-    // so it is ignored here and generated separately when the SYN_STREAM
-    // is sent from SpdyStream31::TransmitFrame
-
-    // NS_NET_STATUS_WAITING_FOR:
-    // Created by nsHttpConnection when the request has been totally sent.
-    // There is no good way to map it to the right transaction in spdy,
-    // so it is ignored here and generated separately when the same
-    // condition is complete in SpdyStream31 when there is no more
-    // request body left to be transmitted.
-
-    // NS_NET_STATUS_RECEIVING_FROM
-    // Generated in spdysession whenever we read a data frame or a syn_reply
-    // that can be attributed to a particular stream/transaction
-
-    break;
-  }
-}
-
-// ReadSegments() is used to write data to the network. Generally, HTTP
-// request data is pulled from the approriate transaction and
-// converted to SPDY data. Sometimes control data like window-update are
-// generated instead.
-
-nsresult
-SpdySession31::ReadSegmentsAgain(nsAHttpSegmentReader *reader,
-                                 uint32_t count,
-                                 uint32_t *countRead,
-                                 bool *again)
-{
-  MOZ_ASSERT(PR_GetCurrentThread() == gSocketThread);
-
-  MOZ_ASSERT(!mSegmentReader || !reader || (mSegmentReader == reader),
-             "Inconsistent Write Function Callback");
-
-  if (reader)
-    mSegmentReader = reader;
-
-  nsresult rv;
-  *countRead = 0;
-
-  LOG3(("SpdySession31::ReadSegments %p", this));
-
-  SpdyStream31 *stream = static_cast<SpdyStream31 *>(mReadyForWrite.PopFront());
-  if (!stream) {
-    LOG3(("SpdySession31 %p could not identify a stream to write; suspending.",
-          this));
-    FlushOutputQueue();
-    SetWriteCallbacks();
-    return NS_BASE_STREAM_WOULD_BLOCK;
-  }
-
-  LOG3(("SpdySession31 %p will write from SpdyStream31 %p 0x%X "
-        "block-input=%d block-output=%d\n", this, stream, stream->StreamID(),
-        stream->RequestBlockedOnRead(), stream->BlockedOnRwin()));
-
-  rv = stream->ReadSegments(this, count, countRead);
-
-  // Not every permutation of stream->ReadSegents produces data (and therefore
-  // tries to flush the output queue) - SENDING_FIN_STREAM can be an example
-  // of that. But we might still have old data buffered that would be good
-  // to flush.
-  FlushOutputQueue();
-
-  // Allow new server reads - that might be data or control information
-  // (e.g. window updates or http replies) that are responses to these writes
-  ResumeRecv();
-
-  if (stream->RequestBlockedOnRead()) {
-
-    // We are blocked waiting for input - either more http headers or
-    // any request body data. When more data from the request stream
-    // becomes available the httptransaction will call conn->ResumeSend().
-
-    LOG3(("SpdySession31::ReadSegments %p dealing with block on read", this));
-
-    // call readsegments again if there are other streams ready
-    // to run in this session
-    if (GetWriteQueueSize())
-      rv = NS_OK;
-    else
-      rv = NS_BASE_STREAM_WOULD_BLOCK;
-    SetWriteCallbacks();
-    return rv;
-  }
-
-  if (NS_FAILED(rv)) {
-    LOG3(("SpdySession31::ReadSegments %p may return FAIL code %X",
-          this, rv));
-    if (rv == NS_BASE_STREAM_WOULD_BLOCK) {
-      return rv;
-    }
-
-    CleanupStream(stream, rv, RST_CANCEL);
-    if (SoftStreamError(rv)) {
-      LOG3(("SpdySession31::ReadSegments %p soft error override\n", this));
-      *again = false;
-      SetWriteCallbacks();
-      rv = NS_OK;
-    }
-    return rv;
-  }
-
-  if (*countRead > 0) {
-    LOG3(("SpdySession31::ReadSegments %p stream=%p countread=%d",
-          this, stream, *countRead));
-    mReadyForWrite.Push(stream);
-    SetWriteCallbacks();
-    return rv;
-  }
-
-  if (stream->BlockedOnRwin()) {
-    LOG3(("SpdySession31 %p will stream %p 0x%X suspended for flow control\n",
-          this, stream, stream->StreamID()));
-    return NS_BASE_STREAM_WOULD_BLOCK;
-  }
-
-  LOG3(("SpdySession31::ReadSegments %p stream=%p stream send complete",
-        this, stream));
-
-  // call readsegments again if there are other streams ready
-  // to go in this session
-  SetWriteCallbacks();
-
-  return rv;
-}
-
-nsresult
-SpdySession31::ReadSegments(nsAHttpSegmentReader *reader,
-                            uint32_t count, uint32_t *countRead)
-{
-  bool again = false;
-  return ReadSegmentsAgain(reader, count, countRead, &again);
-}
-
-// WriteSegments() is used to read data off the socket. Generally this is
-// just the SPDY frame header and from there the appropriate SPDYStream
-// is identified from the Stream-ID. The http transaction associated with
-// that read then pulls in the data directly, which it will feed to
-// OnWriteSegment(). That function will gateway it into http and feed
-// it to the appropriate transaction.
-
-// we call writer->OnWriteSegment via NetworkRead() to get a spdy header..
-// and decide if it is data or control.. if it is control, just deal with it.
-// if it is data, identify the spdy stream
-// call stream->WriteSegments which can call this::OnWriteSegment to get the
-// data. It always gets full frames if they are part of the stream
-
-nsresult
-SpdySession31::WriteSegmentsAgain(nsAHttpSegmentWriter *writer,
-                                  uint32_t count,
-                                  uint32_t *countWritten,
-                                  bool *again)
-{
-  typedef nsresult  (*Control_FX) (SpdySession31 *self);
-  static const Control_FX sControlFunctions[] =
-  {
-      nullptr,
-      SpdySession31::HandleSynStream,
-      SpdySession31::HandleSynReply,
-      SpdySession31::HandleRstStream,
-      SpdySession31::HandleSettings,
-      SpdySession31::HandleNoop,
-      SpdySession31::HandlePing,
-      SpdySession31::HandleGoAway,
-      SpdySession31::HandleHeaders,
-      SpdySession31::HandleWindowUpdate,
-      SpdySession31::HandleCredential
-  };
-
-  MOZ_ASSERT(PR_GetCurrentThread() == gSocketThread);
-
-  nsresult rv;
-  *countWritten = 0;
-
-  if (mClosed)
-    return NS_ERROR_FAILURE;
-
-  SetWriteCallbacks();
-
-  // If there are http transactions attached to a push stream with filled buffers
-  // trigger that data pump here. This only reads from buffers (not the network)
-  // so mDownstreamState doesn't matter.
-  SpdyStream31 *pushConnectedStream =
-    static_cast<SpdyStream31 *>(mReadyForRead.PopFront());
-  if (pushConnectedStream) {
-    LOG3(("SpdySession31::WriteSegments %p processing pushed stream 0x%X\n",
-          this, pushConnectedStream->StreamID()));
-    mSegmentWriter = writer;
-    rv = pushConnectedStream->WriteSegments(this, count, countWritten);
-    mSegmentWriter = nullptr;
-
-    // The pipe in nsHttpTransaction rewrites CLOSED error codes into OK
-    // so we need this check to determine the truth.
-    if (NS_SUCCEEDED(rv) && !*countWritten &&
-        pushConnectedStream->PushSource() &&
-        pushConnectedStream->PushSource()->GetPushComplete()) {
-      rv = NS_BASE_STREAM_CLOSED;
-    }
-
-    if (rv == NS_BASE_STREAM_CLOSED) {
-      CleanupStream(pushConnectedStream, NS_OK, RST_CANCEL);
-      rv = NS_OK;
-    }
-
-    // if we return OK to nsHttpConnection it will use mSocketInCondition
-    // to determine whether to schedule more reads, incorrectly
-    // assuming that nsHttpConnection::OnSocketWrite() was called.
-    if (NS_SUCCEEDED(rv) || rv == NS_BASE_STREAM_WOULD_BLOCK) {
-      rv = NS_BASE_STREAM_WOULD_BLOCK;
-      ResumeRecv();
-    }
-
-    return rv;
-  }
-
-  // We buffer all control frames and act on them in this layer.
-  // We buffer the first 8 bytes of data frames (the header) but
-  // the actual data is passed through unprocessed.
-
-  if (mDownstreamState == BUFFERING_FRAME_HEADER) {
-    // The first 8 bytes of every frame is header information that
-    // we are going to want to strip before passing to http. That is
-    // true of both control and data packets.
-
-    MOZ_ASSERT(mInputFrameBufferUsed < 8,
-               "Frame Buffer Used Too Large for State");
-
-    rv = NetworkRead(writer, &mInputFrameBuffer[mInputFrameBufferUsed],
-                     8 - mInputFrameBufferUsed, countWritten);
-
-    if (NS_FAILED(rv)) {
-      LOG3(("SpdySession31 %p buffering frame header read failure %x\n",
-            this, rv));
-      // maybe just blocked reading from network
-      if (rv == NS_BASE_STREAM_WOULD_BLOCK)
-        rv = NS_OK;
-      return rv;
-    }
-
-    LogIO(this, nullptr, "Reading Frame Header",
-          &mInputFrameBuffer[mInputFrameBufferUsed], *countWritten);
-
-    mInputFrameBufferUsed += *countWritten;
-
-    if (mInputFrameBufferUsed < 8)
-    {
-      LOG3(("SpdySession31::WriteSegments %p "
-            "BUFFERING FRAME HEADER incomplete size=%d",
-            this, mInputFrameBufferUsed));
-      return rv;
-    }
-
-    // For both control and data frames the second 32 bit word of the header
-    // is 8-flags, 24-length. (network byte order)
-    mInputFrameDataSize =
-      PR_ntohl(reinterpret_cast<uint32_t *>(mInputFrameBuffer.get())[1]);
-    mInputFrameDataSize &= 0x00ffffff;
-    mInputFrameDataRead = 0;
-
-    if (mInputFrameBuffer[0] & kFlag_Control) {
-      EnsureBuffer(mInputFrameBuffer, mInputFrameDataSize + 8, 8,
-                   mInputFrameBufferSize);
-      ChangeDownstreamState(BUFFERING_CONTROL_FRAME);
-
-      // The first 32 bit word of the header is
-      // 1 ctrl - 15 version - 16 type
-      uint16_t version =
-        PR_ntohs(reinterpret_cast<uint16_t *>(mInputFrameBuffer.get())[0]);
-      version &= 0x7fff;
-
-      mFrameControlType =
-        PR_ntohs(reinterpret_cast<uint16_t *>(mInputFrameBuffer.get())[1]);
-
-      LOG3(("SpdySession31::WriteSegments %p - Control Frame Identified "
-            "type %d version %d data len %d",
-            this, mFrameControlType, version, mInputFrameDataSize));
-
-      if (mFrameControlType >= CONTROL_TYPE_LAST ||
-          mFrameControlType <= CONTROL_TYPE_FIRST)
-        return NS_ERROR_ILLEGAL_VALUE;
-
-      if (version != kVersion)
-        return NS_ERROR_ILLEGAL_VALUE;
-    }
-    else {
-      ChangeDownstreamState(PROCESSING_DATA_FRAME);
-
-      Telemetry::Accumulate(Telemetry::SPDY_CHUNK_RECVD,
-                            mInputFrameDataSize >> 10);
-      mLastDataReadEpoch = mLastReadEpoch;
-
-      uint32_t streamID =
-        PR_ntohl(reinterpret_cast<uint32_t *>(mInputFrameBuffer.get())[0]);
-      rv = SetInputFrameDataStream(streamID);
-      if (NS_FAILED(rv)) {
-        LOG(("SpdySession31::WriteSegments %p lookup streamID 0x%X failed. "
-             "probably due to verification.\n", this, streamID));
-        return rv;
-      }
-      if (!mInputFrameDataStream) {
-        LOG3(("SpdySession31::WriteSegments %p lookup streamID 0x%X failed. "
-              "Next = 0x%X", this, streamID, mNextStreamID));
-        if (streamID >= mNextStreamID)
-          GenerateRstStream(RST_INVALID_STREAM, streamID);
-        ChangeDownstreamState(DISCARDING_DATA_FRAME);
-      }
-      else if (mInputFrameDataStream->RecvdFin()) {
-        LOG3(("SpdySession31::WriteSegments %p streamID 0x%X "
-              "Data arrived for already server closed stream.\n",
-              this, streamID));
-        GenerateRstStream(RST_STREAM_ALREADY_CLOSED, streamID);
-        ChangeDownstreamState(DISCARDING_DATA_FRAME);
-      }
-      else if (!mInputFrameDataStream->RecvdData()) {
-        LOG3(("SpdySession31 %p First Data Frame Flushes Headers stream 0x%X\n",
-              this, streamID));
-
-        mInputFrameDataStream->SetRecvdData(true);
-        rv = ResponseHeadersComplete();
-        if (rv == NS_ERROR_ILLEGAL_VALUE) {
-          LOG3(("SpdySession31 %p ResponseHeadersComplete PROTOCOL_ERROR detected 0x%X\n",
-                this, streamID));
-          CleanupStream(mInputFrameDataStream, rv, RST_PROTOCOL_ERROR);
-          ChangeDownstreamState(DISCARDING_DATA_FRAME);
-        }
-        else {
-          mDataPending = true;
-        }
-      }
-
-      mInputFrameDataLast = (mInputFrameBuffer[4] & kFlag_Data_FIN);
-      LOG3(("Start Processing Data Frame. "
-            "Session=%p Stream ID 0x%X Stream Ptr %p Fin=%d Len=%d",
-            this, streamID, mInputFrameDataStream, mInputFrameDataLast,
-            mInputFrameDataSize));
-      UpdateLocalRwin(mInputFrameDataStream, mInputFrameDataSize);
-    }
-  }
-
-  if (mDownstreamState == PROCESSING_CONTROL_RST_STREAM) {
-    if (mDownstreamRstReason == RST_REFUSED_STREAM)
-      rv = NS_ERROR_NET_RESET;            //we can retry this 100% safely
-    else if (mDownstreamRstReason == RST_CANCEL) {
-      rv = mInputFrameDataStream->RecvdData() ?
-        NS_ERROR_NET_PARTIAL_TRANSFER :
-        NS_ERROR_NET_INTERRUPT;
-    }
-    else if (mDownstreamRstReason == RST_PROTOCOL_ERROR ||
-             mDownstreamRstReason == RST_INTERNAL_ERROR ||
-             mDownstreamRstReason == RST_UNSUPPORTED_VERSION) {
-      rv = NS_ERROR_NET_INTERRUPT;
-    }
-    else if (mDownstreamRstReason == RST_FRAME_TOO_LARGE)
-      rv = NS_ERROR_FILE_TOO_BIG;
-    else
-      rv = NS_ERROR_ILLEGAL_VALUE;
-
-    if (mDownstreamRstReason != RST_REFUSED_STREAM &&
-        mDownstreamRstReason != RST_CANCEL)
-      mShouldGoAway = true;
-
-    // mInputFrameDataStream is reset by ChangeDownstreamState
-    SpdyStream31 *stream = mInputFrameDataStream;
-    ResetDownstreamState();
-    LOG3(("SpdySession31::WriteSegments cleanup stream on recv of rst "
-          "session=%p stream=%p 0x%X\n", this, stream,
-          stream ? stream->StreamID() : 0));
-    CleanupStream(stream, rv, RST_CANCEL);
-    return NS_OK;
-  }
-
-  if (mDownstreamState == PROCESSING_DATA_FRAME ||
-      mDownstreamState == PROCESSING_COMPLETE_HEADERS) {
-
-    // The cleanup stream should only be set while stream->WriteSegments is
-    // on the stack and then cleaned up in this code block afterwards.
-    MOZ_ASSERT(!mNeedsCleanup, "cleanup stream set unexpectedly");
-    mNeedsCleanup = nullptr;                     /* just in case */
-
-    // The writesegments() stack can clear mInputFrameDataStream so
-    // only reference this local copy of it afterwards
-    SpdyStream31 *stream = mInputFrameDataStream;
-    mSegmentWriter = writer;
-    rv = mInputFrameDataStream->WriteSegments(this, count, countWritten);
-    bool channelPipeFull = false;
-    if (rv == NS_BASE_STREAM_WOULD_BLOCK) {
-      LOG3(("SpdySession31::WriteSegments session=%p stream=%p 0x%X "
-            "stream channel pipe full\n",
-            this, stream, stream ? stream->StreamID() : 0));
-      channelPipeFull = stream->ChannelPipeFull();
-    }
-    mSegmentWriter = nullptr;
-
-    mLastDataReadEpoch = mLastReadEpoch;
-
-    if (SoftStreamError(rv)) {
-      // This will happen when the transaction figures out it is EOF, generally
-      // due to a content-length match being made. Return OK from this function
-      // otherwise the whole session would be torn down.
-
-      // if we were doing PROCESSING_COMPLETE_HEADERS need to pop the state
-      // back to PROCESSING_DATA_FRAME where we came from
-      mDownstreamState = PROCESSING_DATA_FRAME;
-
-      if (mInputFrameDataRead == mInputFrameDataSize)
-        ResetDownstreamState();
-      LOG3(("SpdySession31::WriteSegments session=%p stream=%p 0x%X "
-            "needscleanup=%p. cleanup stream based on "
-            "stream->writeSegments returning code %X\n",
-            this, stream, stream ? stream->StreamID() : 0,
-            mNeedsCleanup, rv));
-      CleanupStream(stream, NS_OK, RST_CANCEL);
-      MOZ_ASSERT(!mNeedsCleanup || mNeedsCleanup == stream);
-      mNeedsCleanup = nullptr;
-      *again = false;
-      ResumeRecv();
-      return NS_OK;
-    }
-
-    if (mNeedsCleanup) {
-      LOG3(("SpdySession31::WriteSegments session=%p stream=%p 0x%X "
-            "cleanup stream based on mNeedsCleanup.\n",
-            this, mNeedsCleanup, mNeedsCleanup ? mNeedsCleanup->StreamID() : 0));
-      CleanupStream(mNeedsCleanup, NS_OK, RST_CANCEL);
-      mNeedsCleanup = nullptr;
-    }
-
-    if (NS_FAILED(rv)) {
-      LOG3(("SpdySession31::WriteSegments session=%p stream=%p 0x%X "
-            "data frame read failure %x pipefull=%d\n",
-            this, stream, stream ? stream->StreamID() : 0, rv, channelPipeFull));
-      // maybe just blocked reading from network
-      if ((rv == NS_BASE_STREAM_WOULD_BLOCK) && !channelPipeFull) {
-        rv = NS_OK;
-      }
-    }
-
-    return rv;
-  }
-
-  if (mDownstreamState == DISCARDING_DATA_FRAME) {
-    char trash[4096];
-    uint32_t discardCount = std::min(mInputFrameDataSize - mInputFrameDataRead,
-                                     4096U);
-
-    if (!discardCount) {
-      ResetDownstreamState();
-      ResumeRecv();
-      return NS_BASE_STREAM_WOULD_BLOCK;
-    }
-
-    rv = NetworkRead(writer, trash, discardCount, countWritten);
-
-    if (NS_FAILED(rv)) {
-      LOG3(("SpdySession31 %p discard frame read failure %x\n", this, rv));
-      // maybe just blocked reading from network
-      if (rv == NS_BASE_STREAM_WOULD_BLOCK)
-        rv = NS_OK;
-      return rv;
-    }
-
-    LogIO(this, nullptr, "Discarding Frame", trash, *countWritten);
-
-    mInputFrameDataRead += *countWritten;
-
-    if (mInputFrameDataRead == mInputFrameDataSize)
-      ResetDownstreamState();
-    return rv;
-  }
-
-  MOZ_ASSERT(mDownstreamState == BUFFERING_CONTROL_FRAME);
-  if (mDownstreamState != BUFFERING_CONTROL_FRAME) {
-    // this cannot happen
-    return NS_ERROR_UNEXPECTED;
-  }
-
-  MOZ_ASSERT(mInputFrameBufferUsed == 8,
-             "Frame Buffer Header Not Present");
-
-  rv = NetworkRead(writer, &mInputFrameBuffer[8 + mInputFrameDataRead],
-                   mInputFrameDataSize - mInputFrameDataRead, countWritten);
-
-  if (NS_FAILED(rv)) {
-    LOG3(("SpdySession31 %p buffering control frame read failure %x\n",
-          this, rv));
-    // maybe just blocked reading from network
-    if (rv == NS_BASE_STREAM_WOULD_BLOCK)
-      rv = NS_OK;
-    return rv;
-  }
-
-  LogIO(this, nullptr, "Reading Control Frame",
-        &mInputFrameBuffer[8 + mInputFrameDataRead], *countWritten);
-
-  mInputFrameDataRead += *countWritten;
-
-  if (mInputFrameDataRead != mInputFrameDataSize)
-    return NS_OK;
-
-  // This check is actually redundant, the control type was previously
-  // checked to make sure it was in range, but we will check it again
-  // at time of use to make sure a regression doesn't creep in.
-  if (mFrameControlType >= CONTROL_TYPE_LAST ||
-      mFrameControlType <= CONTROL_TYPE_FIRST)
-  {
-    MOZ_ASSERT(false, "control type out of range");
-    return NS_ERROR_ILLEGAL_VALUE;
-  }
-  rv = sControlFunctions[mFrameControlType](this);
-
-  MOZ_ASSERT(NS_FAILED(rv) ||
-             mDownstreamState != BUFFERING_CONTROL_FRAME,
-             "Control Handler returned OK but did not change state");
-
-  if (mShouldGoAway && !mStreamTransactionHash.Count())
-    Close(NS_OK);
-  return rv;
-}
-
-nsresult
-SpdySession31::WriteSegments(nsAHttpSegmentWriter *writer,
-                             uint32_t count, uint32_t *countWritten)
-{
-  bool again = false;
-  return WriteSegmentsAgain(writer, count, countWritten, &again);
-}
-
-void
-SpdySession31::UpdateLocalStreamWindow(SpdyStream31 *stream,
-                                       uint32_t bytes)
-{
-  if (!stream) // this is ok - it means there was a data frame for a rst stream
-    return;
-
-  stream->DecrementLocalWindow(bytes);
-
-  // If this data packet was not for a valid or live stream then there
-  // is no reason to mess with the flow control
-  if (stream->RecvdFin())
-    return;
-
-  // Don't necessarily ack every data packet. Only do it
-  // after a significant amount of data.
-  uint64_t unacked = stream->LocalUnAcked();
-  int64_t  localWindow = stream->LocalWindow();
-
-  LOG3(("SpdySession31::UpdateLocalStreamWindow this=%p id=0x%X newbytes=%u "
-        "unacked=%llu localWindow=%lld\n",
-        this, stream->StreamID(), bytes, unacked, localWindow));
-
-  if (!unacked)
-    return;
-
-  if ((unacked < kMinimumToAck) && (localWindow > kEmergencyWindowThreshold))
-    return;
-
-  if (!stream->HasSink()) {
-    LOG3(("SpdySession31::UpdateLocalStreamWindow %p 0x%X Pushed Stream Has No Sink\n",
-          this, stream->StreamID()));
-    return;
-  }
-
-  // Generate window updates directly out of spdysession instead of the stream
-  // in order to avoid queue delays in getting the 'ACK' out.
-  uint32_t toack = (unacked <= 0x7fffffffU) ? unacked : 0x7fffffffU;
-
-  LOG3(("SpdySession31::UpdateLocalStreamWindow Ack this=%p id=0x%X acksize=%d\n",
-        this, stream->StreamID(), toack));
-  stream->IncrementLocalWindow(toack);
-
-  // room for this packet needs to be ensured before calling this function
-  static const uint32_t dataLen = 8;
-  char *packet = mOutputQueueBuffer.get() + mOutputQueueUsed;
-  mOutputQueueUsed += 8 + dataLen;
-  MOZ_ASSERT(mOutputQueueUsed <= mOutputQueueSize);
-
-  memset(packet, 0, 8 + dataLen);
-  packet[0] = kFlag_Control;
-  packet[1] = kVersion;
-  packet[3] = CONTROL_TYPE_WINDOW_UPDATE;
-  packet[7] = dataLen;
-
-  uint32_t id = PR_htonl(stream->StreamID());
-  memcpy(packet + 8, &id, 4);
-  toack = PR_htonl(toack);
-  memcpy(packet + 12, &toack, 4);
-
-  LogIO(this, stream, "Stream Window Update", packet, 8 + dataLen);
-  // dont flush here, this write can commonly be coalesced with a
-  // session window update to immediately follow.
-}
-
-void
-SpdySession31::UpdateLocalSessionWindow(uint32_t bytes)
-{
-  if (!bytes)
-    return;
-
-  mLocalSessionWindow -= bytes;
-
-  LOG3(("SpdySession31::UpdateLocalSessionWindow this=%p newbytes=%u "
-        "localWindow=%lld\n", this, bytes, mLocalSessionWindow));
-
-  // Don't necessarily ack every data packet. Only do it
-  // after a significant amount of data.
-  if ((mLocalSessionWindow > (ASpdySession::kInitialRwin - kMinimumToAck)) &&
-      (mLocalSessionWindow > kEmergencyWindowThreshold))
-    return;
-
-  // Only send max 31 bits of window updates at a time.
-  uint64_t toack64 = ASpdySession::kInitialRwin - mLocalSessionWindow;
-  uint32_t toack = (toack64 <= 0x7fffffffU) ? toack64 : 0x7fffffffU;
-
-  LOG3(("SpdySession31::UpdateLocalSessionWindow Ack this=%p acksize=%u\n",
-        this, toack));
-  mLocalSessionWindow += toack;
-
-  // room for this packet needs to be ensured before calling this function
-  static const uint32_t dataLen = 8;
-  char *packet = mOutputQueueBuffer.get() + mOutputQueueUsed;
-  mOutputQueueUsed += 8 + dataLen;
-  MOZ_ASSERT(mOutputQueueUsed <= mOutputQueueSize);
-
-  memset(packet, 0, 8 + dataLen);
-  packet[0] = kFlag_Control;
-  packet[1] = kVersion;
-  packet[3] = CONTROL_TYPE_WINDOW_UPDATE;
-  packet[7] = dataLen;
-
-  // packet 8-11 is ID and left at 0 for session ID
-  toack = PR_htonl(toack);
-  memcpy(packet + 12, &toack, 4);
-
-  LogIO(this, nullptr, "Session Window Update", packet, 8 + dataLen);
-  // dont flush here, this write can commonly be coalesced with others
-}
-
-void
-SpdySession31::UpdateLocalRwin(SpdyStream31 *stream,
-                               uint32_t bytes)
-{
-  // make sure there is room for 2 window updates even though
-  // we may not generate any.
-  EnsureBuffer(mOutputQueueBuffer, mOutputQueueUsed + (16 *2),
-               mOutputQueueUsed, mOutputQueueSize);
-
-  UpdateLocalStreamWindow(stream, bytes);
-  UpdateLocalSessionWindow(bytes);
-  FlushOutputQueue();
-}
-
-void
-SpdySession31::Close(nsresult aReason)
-{
-  MOZ_ASSERT(PR_GetCurrentThread() == gSocketThread);
-
-  if (mClosed)
-    return;
-
-  LOG3(("SpdySession31::Close %p %X", this, aReason));
-
-  mClosed = true;
-
-  Shutdown();
-
-  mStreamIDHash.Clear();
-  mStreamTransactionHash.Clear();
-
-  uint32_t goAwayReason;
-  if (NS_SUCCEEDED(aReason)) {
-    goAwayReason = OK;
-  } else if (aReason == NS_ERROR_ILLEGAL_VALUE) {
-    goAwayReason = PROTOCOL_ERROR;
-  } else {
-    goAwayReason = INTERNAL_ERROR;
-  }
-  GenerateGoAway(goAwayReason);
-  mConnection = nullptr;
-  mSegmentReader = nullptr;
-  mSegmentWriter = nullptr;
-}
-
-nsHttpConnectionInfo *
-SpdySession31::ConnectionInfo()
-{
-  RefPtr<nsHttpConnectionInfo> ci;
-  GetConnectionInfo(getter_AddRefs(ci));
-  return ci.get();
-}
-
-void
-SpdySession31::CloseTransaction(nsAHttpTransaction *aTransaction,
-                                nsresult aResult)
-{
-  MOZ_ASSERT(PR_GetCurrentThread() == gSocketThread);
-  LOG3(("SpdySession31::CloseTransaction %p %p %x", this, aTransaction, aResult));
-
-  // Generally this arrives as a cancel event from the connection manager.
-
-  // need to find the stream and call CleanupStream() on it.
-  SpdyStream31 *stream = mStreamTransactionHash.Get(aTransaction);
-  if (!stream) {
-    LOG3(("SpdySession31::CloseTransaction %p %p %x - not found.",
-          this, aTransaction, aResult));
-    return;
-  }
-  LOG3(("SpdySession31::CloseTransaction probably a cancel. "
-        "this=%p, trans=%p, result=%x, streamID=0x%X stream=%p",
-        this, aTransaction, aResult, stream->StreamID(), stream));
-  CleanupStream(stream, aResult, RST_CANCEL);
-  ResumeRecv();
-}
-
-//-----------------------------------------------------------------------------
-// nsAHttpSegmentReader
-//-----------------------------------------------------------------------------
-
-nsresult
-SpdySession31::OnReadSegment(const char *buf,
-                             uint32_t count,
-                             uint32_t *countRead)
-{
-  MOZ_ASSERT(PR_GetCurrentThread() == gSocketThread);
-
-  nsresult rv;
-
-  // If we can release old queued data then we can try and write the new
-  // data directly to the network without using the output queue at all
-  if (mOutputQueueUsed)
-    FlushOutputQueue();
-
-  if (!mOutputQueueUsed && mSegmentReader) {
-    // try and write directly without output queue
-    rv = mSegmentReader->OnReadSegment(buf, count, countRead);
-
-    if (rv == NS_BASE_STREAM_WOULD_BLOCK)
-      *countRead = 0;
-    else if (NS_FAILED(rv))
-      return rv;
-
-    if (*countRead < count) {
-      uint32_t required = count - *countRead;
-      // assuming a commitment() happened, this ensurebuffer is a nop
-      // but just in case the queuesize is too small for the required data
-      // call ensurebuffer().
-      EnsureBuffer(mOutputQueueBuffer, required, 0, mOutputQueueSize);
-      memcpy(mOutputQueueBuffer.get(), buf + *countRead, required);
-      mOutputQueueUsed = required;
-    }
-
-    *countRead = count;
-    return NS_OK;
-  }
-
-  // At this point we are going to buffer the new data in the output
-  // queue if it fits. By coalescing multiple small submissions into one larger
-  // buffer we can get larger writes out to the network later on.
-
-  // This routine should not be allowed to fill up the output queue
-  // all on its own - at least kQueueReserved bytes are always left
-  // for other routines to use - but this is an all-or-nothing function,
-  // so if it will not all fit just return WOULD_BLOCK
-
-  if ((mOutputQueueUsed + count) > (mOutputQueueSize - kQueueReserved))
-    return NS_BASE_STREAM_WOULD_BLOCK;
-
-  memcpy(mOutputQueueBuffer.get() + mOutputQueueUsed, buf, count);
-  mOutputQueueUsed += count;
-  *countRead = count;
-
-  FlushOutputQueue();
-
-  return NS_OK;
-}
-
-nsresult
-SpdySession31::CommitToSegmentSize(uint32_t count, bool forceCommitment)
-{
-  if (mOutputQueueUsed)
-    FlushOutputQueue();
-
-  // would there be enough room to buffer this if needed?
-  if ((mOutputQueueUsed + count) <= (mOutputQueueSize - kQueueReserved))
-    return NS_OK;
-
-  // if we are using part of our buffers already, try again later unless
-  // forceCommitment is set.
-  if (mOutputQueueUsed && !forceCommitment)
-    return NS_BASE_STREAM_WOULD_BLOCK;
-
-  if (mOutputQueueUsed) {
-    // normally we avoid the memmove of RealignOutputQueue, but we'll try
-    // it if forceCommitment is set before growing the buffer.
-    RealignOutputQueue();
-
-    // is there enough room now?
-    if ((mOutputQueueUsed + count) <= (mOutputQueueSize - kQueueReserved))
-      return NS_OK;
-  }
-
-  // resize the buffers as needed
-  EnsureBuffer(mOutputQueueBuffer, mOutputQueueUsed + count + kQueueReserved,
-               mOutputQueueUsed, mOutputQueueSize);
-
-  MOZ_ASSERT((mOutputQueueUsed + count) <= (mOutputQueueSize - kQueueReserved),
-             "buffer not as large as expected");
-
-  return NS_OK;
-}
-
-//-----------------------------------------------------------------------------
-// nsAHttpSegmentWriter
-//-----------------------------------------------------------------------------
-
-nsresult
-SpdySession31::OnWriteSegment(char *buf,
-                              uint32_t count,
-                              uint32_t *countWritten)
-{
-  MOZ_ASSERT(PR_GetCurrentThread() == gSocketThread);
-  nsresult rv;
-
-  if (!mSegmentWriter) {
-    // the only way this could happen would be if Close() were called on the
-    // stack with WriteSegments()
-    return NS_ERROR_FAILURE;
-  }
-
-  if (mDownstreamState == PROCESSING_DATA_FRAME) {
-
-    if (mInputFrameDataLast &&
-        mInputFrameDataRead == mInputFrameDataSize) {
-      *countWritten = 0;
-      SetNeedsCleanup();
-      return NS_BASE_STREAM_CLOSED;
-    }
-
-    count = std::min(count, mInputFrameDataSize - mInputFrameDataRead);
-    rv = NetworkRead(mSegmentWriter, buf, count, countWritten);
-    if (NS_FAILED(rv))
-      return rv;
-
-    LogIO(this, mInputFrameDataStream, "Reading Data Frame",
-          buf, *countWritten);
-
-    mInputFrameDataRead += *countWritten;
-
-    mInputFrameDataStream->UpdateTransportReadEvents(*countWritten);
-    if ((mInputFrameDataRead == mInputFrameDataSize) && !mInputFrameDataLast)
-      ResetDownstreamState();
-
-    return rv;
-  }
-
-  if (mDownstreamState == PROCESSING_COMPLETE_HEADERS) {
-
-    if (mFlatHTTPResponseHeaders.Length() == mFlatHTTPResponseHeadersOut &&
-        mInputFrameDataLast) {
-      *countWritten = 0;
-      SetNeedsCleanup();
-      return NS_BASE_STREAM_CLOSED;
-    }
-
-    count = std::min(count,
-                     mFlatHTTPResponseHeaders.Length() -
-                     mFlatHTTPResponseHeadersOut);
-    memcpy(buf,
-           mFlatHTTPResponseHeaders.get() + mFlatHTTPResponseHeadersOut,
-           count);
-    mFlatHTTPResponseHeadersOut += count;
-    *countWritten = count;
-
-    if (mFlatHTTPResponseHeaders.Length() == mFlatHTTPResponseHeadersOut) {
-      if (mDataPending) {
-        // Now ready to process data frames - pop PROCESING_DATA_FRAME back onto
-        // the stack because receipt of that first data frame triggered the
-        // response header processing
-        mDataPending = false;
-        ChangeDownstreamState(PROCESSING_DATA_FRAME);
-      }
-      else if (!mInputFrameDataLast) {
-        // If more frames are expected in this stream, then reset the state so they can be
-        // handled. Otherwise (e.g. a 0 length response with the fin on the SYN_REPLY)
-        // stay in PROCESSING_COMPLETE_HEADERS state so the SetNeedsCleanup() code above can
-        // cleanup the stream.
-        ResetDownstreamState();
-      }
-    }
-
-    return NS_OK;
-  }
-
-  return NS_ERROR_UNEXPECTED;
-}
-
-void
-SpdySession31::SetNeedsCleanup()
-{
-  LOG3(("SpdySession31::SetNeedsCleanup %p - recorded downstream fin of "
-        "stream %p 0x%X", this, mInputFrameDataStream,
-        mInputFrameDataStream->StreamID()));
-
-  // This will result in Close() being called
-  MOZ_ASSERT(!mNeedsCleanup, "mNeedsCleanup unexpectedly set");
-  mInputFrameDataStream->SetResponseIsComplete();
-  mNeedsCleanup = mInputFrameDataStream;
-  ResetDownstreamState();
-}
-
-void
-SpdySession31::ConnectPushedStream(SpdyStream31 *stream)
-{
-  mReadyForRead.Push(stream);
-  ForceRecv();
-}
-
-uint32_t
-SpdySession31::FindTunnelCount(nsHttpConnectionInfo *aConnInfo)
-{
-  MOZ_ASSERT(PR_GetCurrentThread() == gSocketThread);
-  uint32_t rv = 0;
-  mTunnelHash.Get(aConnInfo->HashKey(), &rv);
-  return rv;
-}
-
-void
-SpdySession31::RegisterTunnel(SpdyStream31 *aTunnel)
-{
-  MOZ_ASSERT(PR_GetCurrentThread() == gSocketThread);
-  nsHttpConnectionInfo *ci = aTunnel->Transaction()->ConnectionInfo();
-  uint32_t newcount = FindTunnelCount(ci) + 1;
-  mTunnelHash.Remove(ci->HashKey());
-  mTunnelHash.Put(ci->HashKey(), newcount);
-  LOG3(("SpdySession31::RegisterTunnel %p stream=%p tunnels=%d [%s]",
-        this, aTunnel, newcount, ci->HashKey().get()));
-}
-
-void
-SpdySession31::UnRegisterTunnel(SpdyStream31 *aTunnel)
-{
-  MOZ_ASSERT(PR_GetCurrentThread() == gSocketThread);
-  nsHttpConnectionInfo *ci = aTunnel->Transaction()->ConnectionInfo();
-  MOZ_ASSERT(FindTunnelCount(ci));
-  uint32_t newcount = FindTunnelCount(ci) - 1;
-  mTunnelHash.Remove(ci->HashKey());
-  if (newcount) {
-    mTunnelHash.Put(ci->HashKey(), newcount);
-  }
-  LOG3(("SpdySession31::UnRegisterTunnel %p stream=%p tunnels=%d [%s]",
-        this, aTunnel, newcount, ci->HashKey().get()));
-}
-
-void
-SpdySession31::CreateTunnel(nsHttpTransaction *trans,
-                            nsHttpConnectionInfo *ci,
-                            nsIInterfaceRequestor *aCallbacks)
-{
-  LOG(("SpdySession31::CreateTunnel %p %p make new tunnel\n", this, trans));
-  // The connect transaction will hold onto the underlying http
-  // transaction so that an auth created by the connect can be mappped
-  // to the correct security callbacks
-
-  RefPtr<SpdyConnectTransaction> connectTrans =
-    new SpdyConnectTransaction(ci, aCallbacks, trans->Caps(), trans, this);
-  AddStream(connectTrans, nsISupportsPriority::PRIORITY_NORMAL, false, nullptr);
-  SpdyStream31 *tunnel = mStreamTransactionHash.Get(connectTrans);
-  MOZ_ASSERT(tunnel);
-  RegisterTunnel(tunnel);
-}
-
-void
-SpdySession31::DispatchOnTunnel(nsAHttpTransaction *aHttpTransaction,
-                                nsIInterfaceRequestor *aCallbacks)
-{
-  MOZ_ASSERT(PR_GetCurrentThread() == gSocketThread);
-  nsHttpTransaction *trans = aHttpTransaction->QueryHttpTransaction();
-  MOZ_ASSERT(trans);
-
-  LOG3(("SpdySession31::DispatchOnTunnel %p trans=%p", this, trans));
-
-  aHttpTransaction->SetConnection(nullptr);
-
-  // this transaction has done its work of setting up a tunnel, let
-  // the connection manager queue it if necessary
-  trans->SetTunnelProvider(this);
-  trans->EnableKeepAlive();
-
-  nsHttpConnectionInfo *ci = aHttpTransaction->ConnectionInfo();
-  if (FindTunnelCount(ci) < gHttpHandler->MaxConnectionsPerOrigin()) {
-    LOG3(("SpdySession31::DispatchOnTunnel %p create on new tunnel %s",
-          this, ci->HashKey().get()));
-    CreateTunnel(trans, ci, aCallbacks);
-  } else {
-    // requeue it. The connection manager is responsible for actually putting
-    // this on the tunnel connection with the specific ci. If that can't
-    // happen the cmgr checks with us via MaybeReTunnel() to see if it should
-    // make a new tunnel or just wait longer.
-    LOG3(("SpdySession31::DispatchOnTunnel %p trans=%p queue in connection manager",
-          this, trans));
-    gHttpHandler->InitiateTransaction(trans, trans->Priority());
-  }
-}
-
-// From ASpdySession
-bool
-SpdySession31::MaybeReTunnel(nsAHttpTransaction *aHttpTransaction)
-{
-  MOZ_ASSERT(PR_GetCurrentThread() == gSocketThread);
-  nsHttpTransaction *trans = aHttpTransaction->QueryHttpTransaction();
-  LOG(("SpdySession31::MaybeReTunnel %p trans=%p\n", this, trans));
-  nsHttpConnectionInfo *ci = aHttpTransaction->ConnectionInfo();
-  if (!trans || trans->TunnelProvider() != this) {
-    // this isn't really one of our transactions.
-    return false;
-  }
-
-  if (mClosed || mShouldGoAway) {
-    LOG(("SpdySession31::MaybeReTunnel %p %p session closed - requeue\n", this, trans));
-    trans->SetTunnelProvider(nullptr);
-    gHttpHandler->InitiateTransaction(trans, trans->Priority());
-    return true;
-  }
-
-  LOG(("SpdySession31::MaybeReTunnel %p %p count=%d limit %d\n",
-       this, trans, FindTunnelCount(ci), gHttpHandler->MaxConnectionsPerOrigin()));
-  if (FindTunnelCount(ci) >= gHttpHandler->MaxConnectionsPerOrigin()) {
-    // patience - a tunnel will open up.
-    return false;
-  }
-
-  LOG(("SpdySession31::MaybeReTunnel %p %p make new tunnel\n", this, trans));
-  CreateTunnel(trans, ci, trans->SecurityCallbacks());
-  return true;
-}
-
-nsresult
-SpdySession31::BufferOutput(const char *buf,
-                            uint32_t count,
-                            uint32_t *countRead)
-{
-  nsAHttpSegmentReader *old = mSegmentReader;
-  mSegmentReader = nullptr;
-  nsresult rv = OnReadSegment(buf, count, countRead);
-  mSegmentReader = old;
-  return rv;
-}
-
-//-----------------------------------------------------------------------------
-// Modified methods of nsAHttpConnection
-//-----------------------------------------------------------------------------
-
-void
-SpdySession31::TransactionHasDataToWrite(nsAHttpTransaction *caller)
-{
-  MOZ_ASSERT(PR_GetCurrentThread() == gSocketThread);
-  LOG3(("SpdySession31::TransactionHasDataToWrite %p trans=%p", this, caller));
-
-  // a trapped signal from the http transaction to the connection that
-  // it is no longer blocked on read.
-
-  SpdyStream31 *stream = mStreamTransactionHash.Get(caller);
-  if (!stream || !VerifyStream(stream)) {
-    LOG3(("SpdySession31::TransactionHasDataToWrite %p caller %p not found",
-          this, caller));
-    return;
-  }
-
-  LOG3(("SpdySession31::TransactionHasDataToWrite %p ID is 0x%X\n",
-        this, stream->StreamID()));
-
-  if (!mClosed) {
-    mReadyForWrite.Push(stream);
-    SetWriteCallbacks();
-  } else {
-    LOG3(("SpdySession31::TransactionHasDataToWrite %p closed so not setting Ready4Write\n",
-          this));
-  }
-
-  // NSPR poll will not poll the network if there are non system PR_FileDesc's
-  // that are ready - so we can get into a deadlock waiting for the system IO
-  // to come back here if we don't force the send loop manually.
-  ForceSend();
-}
-
-void
-SpdySession31::TransactionHasDataToWrite(SpdyStream31 *stream)
-{
-  MOZ_ASSERT(PR_GetCurrentThread() == gSocketThread);
-  LOG3(("SpdySession31::TransactionHasDataToWrite %p stream=%p ID=%x",
-        this, stream, stream->StreamID()));
-
-  mReadyForWrite.Push(stream);
-  SetWriteCallbacks();
-  ForceSend();
-}
-
-bool
-SpdySession31::IsPersistent()
-{
-  return true;
-}
-
-nsresult
-SpdySession31::TakeTransport(nsISocketTransport **,
-                             nsIAsyncInputStream **,
-                             nsIAsyncOutputStream **)
-{
-  MOZ_ASSERT(false, "TakeTransport of SpdySession31");
-  return NS_ERROR_UNEXPECTED;
-}
-
-already_AddRefed<nsHttpConnection>
-SpdySession31::TakeHttpConnection()
-{
-  MOZ_ASSERT(false, "TakeHttpConnection of SpdySession31");
-  return nullptr;
-}
-
-uint32_t
-SpdySession31::CancelPipeline(nsresult reason)
-{
-  // we don't pipeline inside spdy, so this isn't an issue
-  return 0;
-}
-
-nsAHttpTransaction::Classifier
-SpdySession31::Classification()
-{
-  if (!mConnection)
-    return nsAHttpTransaction::CLASS_GENERAL;
-  return mConnection->Classification();
-}
-
-void
-SpdySession31::GetSecurityCallbacks(nsIInterfaceRequestor **aOut)
-{
-  *aOut = nullptr;
-}
-
-//-----------------------------------------------------------------------------
-// unused methods of nsAHttpTransaction
-// We can be sure of this because SpdySession31 is only constructed in
-// nsHttpConnection and is never passed out of that object or a TLSFilterTransaction
-// TLS tunnel
-//-----------------------------------------------------------------------------
-
-void
-SpdySession31::SetConnection(nsAHttpConnection *)
-{
-  // This is unexpected
-  MOZ_ASSERT(false, "SpdySession31::SetConnection()");
-}
-
-void
-SpdySession31::SetProxyConnectFailed()
-{
-  MOZ_ASSERT(false, "SpdySession31::SetProxyConnectFailed()");
-}
-
-bool
-SpdySession31::IsDone()
-{
-  return !mStreamTransactionHash.Count();
-}
-
-nsresult
-SpdySession31::Status()
-{
-  MOZ_ASSERT(false, "SpdySession31::Status()");
-  return NS_ERROR_UNEXPECTED;
-}
-
-uint32_t
-SpdySession31::Caps()
-{
-  MOZ_ASSERT(false, "SpdySession31::Caps()");
-  return 0;
-}
-
-void
-SpdySession31::SetDNSWasRefreshed()
-{
-}
-
-uint64_t
-SpdySession31::Available()
-{
-  MOZ_ASSERT(false, "SpdySession31::Available()");
-  return 0;
-}
-
-nsHttpRequestHead *
-SpdySession31::RequestHead()
-{
-  MOZ_ASSERT(PR_GetCurrentThread() == gSocketThread);
-  MOZ_ASSERT(false,
-             "SpdySession31::RequestHead() "
-             "should not be called after SPDY is setup");
-  return nullptr;
-}
-
-uint32_t
-SpdySession31::Http1xTransactionCount()
-{
-  return 0;
-}
-
-nsresult
-SpdySession31::TakeSubTransactions(
-  nsTArray<RefPtr<nsAHttpTransaction> > &outTransactions)
-{
-  // Generally this cannot be done with spdy as transactions are
-  // started right away.
-
-  LOG3(("SpdySession31::TakeSubTransactions %p\n", this));
-
-  if (mConcurrentHighWater > 0)
-    return NS_ERROR_ALREADY_OPENED;
-
-  LOG3(("   taking %d\n", mStreamTransactionHash.Count()));
-
-  for (auto iter = mStreamTransactionHash.Iter(); !iter.Done(); iter.Next()) {
-    outTransactions.AppendElement(iter.Key());
-
-    // Removing the stream from the hash will delete the stream and drop the
-    // transaction reference the hash held.
-    iter.Remove();
-  }
-  return NS_OK;
-}
-
-nsresult
-SpdySession31::AddTransaction(nsAHttpTransaction *)
-{
-  // This API is meant for pipelining, SpdySession31's should be
-  // extended with AddStream()
-
-  MOZ_ASSERT(false,
-             "SpdySession31::AddTransaction() should not be called");
-
-  return NS_ERROR_NOT_IMPLEMENTED;
-}
-
-uint32_t
-SpdySession31::PipelineDepth()
-{
-  return IsDone() ? 0 : 1;
-}
-
-nsresult
-SpdySession31::SetPipelinePosition(int32_t position)
-{
-  // This API is meant for pipelining, SpdySession31's should be
-  // extended with AddStream()
-
-  MOZ_ASSERT(false,
-             "SpdySession31::SetPipelinePosition() should not be called");
-
-  return NS_ERROR_NOT_IMPLEMENTED;
-}
-
-int32_t
-SpdySession31::PipelinePosition()
-{
-  return 0;
-}
-
-//-----------------------------------------------------------------------------
-// Pass through methods of nsAHttpConnection
-//-----------------------------------------------------------------------------
-
-nsAHttpConnection *
-SpdySession31::Connection()
-{
-  MOZ_ASSERT(PR_GetCurrentThread() == gSocketThread);
-  return mConnection;
-}
-
-nsresult
-SpdySession31::OnHeadersAvailable(nsAHttpTransaction *transaction,
-                                  nsHttpRequestHead *requestHead,
-                                  nsHttpResponseHead *responseHead,
-                                  bool *reset)
-{
-  return mConnection->OnHeadersAvailable(transaction,
-                                         requestHead,
-                                         responseHead,
-                                         reset);
-}
-
-bool
-SpdySession31::IsReused()
-{
-  return mConnection->IsReused();
-}
-
-nsresult
-SpdySession31::PushBack(const char *buf, uint32_t len)
-{
-  return mConnection->PushBack(buf, len);
-}
-
-void
-SpdySession31::SendPing()
-{
-  MOZ_ASSERT(PR_GetCurrentThread() == gSocketThread);
-
-  if (mPreviousUsed) {
-    // alredy in progress, get out
-    return;
-  }
-
-  mPingSentEpoch = PR_IntervalNow();
-  if (!mPingSentEpoch) {
-    mPingSentEpoch = 1; // avoid the 0 sentinel value
-  }
-  if (!mPingThreshold ||
-      (mPingThreshold >  gHttpHandler->NetworkChangedTimeout())) {
-    mPreviousPingThreshold = mPingThreshold;
-    mPreviousUsed = true;
-    mPingThreshold = gHttpHandler->NetworkChangedTimeout();
-  }
-
-  GeneratePing(mNextPingID);
-  mNextPingID += 2;
-  ResumeRecv();
-
-  gHttpHandler->ConnMgr()->ActivateTimeoutTick();
-}
-
-} // namespace net
-} // namespace mozilla
deleted file mode 100644
--- a/netwerk/protocol/http/SpdySession31.h
+++ /dev/null
@@ -1,422 +0,0 @@
-/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
-/* This Source Code Form is subject to the terms of the Mozilla Public
- * License, v. 2.0. If a copy of the MPL was not distributed with this
- * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
-
-#ifndef mozilla_net_SpdySession31_h
-#define mozilla_net_SpdySession31_h
-
-// spdy/3.1
-
-#include "ASpdySession.h"
-#include "mozilla/Attributes.h"
-#include "mozilla/UniquePtr.h"
-#include "nsAHttpConnection.h"
-#include "nsClassHashtable.h"
-#include "nsDataHashtable.h"
-#include "nsDeque.h"
-#include "nsHashKeys.h"
-#include "zlib.h"
-
-class nsISocketTransport;
-
-namespace mozilla { namespace net {
-
-class SpdyPushedStream31;
-class SpdyStream31;
-class nsHttpTransaction;
-
-class SpdySession31 final : public ASpdySession
-                          , public nsAHttpConnection
-                          , public nsAHttpSegmentReader
-                          , public nsAHttpSegmentWriter
-{
-  ~SpdySession31();
-
-public:
-  NS_DECL_THREADSAFE_ISUPPORTS
-  NS_DECL_NSAHTTPTRANSACTION
-  NS_DECL_NSAHTTPCONNECTION(mConnection)
-  NS_DECL_NSAHTTPSEGMENTREADER
-  NS_DECL_NSAHTTPSEGMENTWRITER
-
-  explicit SpdySession31(nsISocketTransport *);
-
-  bool AddStream(nsAHttpTransaction *, int32_t,
-                 bool, nsIInterfaceRequestor *) override;
-  bool CanReuse() override { return !mShouldGoAway && !mClosed; }
-  bool RoomForMoreStreams() override;
-
-  // When the connection is active this is called up to once every 1 second
-  // return the interval (in seconds) that the connection next wants to
-  // have this invoked. It might happen sooner depending on the needs of
-  // other connections.
-  uint32_t  ReadTimeoutTick(PRIntervalTime now) override;
-
-  // Idle time represents time since "goodput".. e.g. a data or header frame
-  PRIntervalTime IdleTime() override;
-
-  // Registering with a newID of 0 means pick the next available odd ID
-  uint32_t RegisterStreamID(SpdyStream31 *, uint32_t aNewID = 0);
-
-  const static uint8_t kVersion        = 3;
-
-  const static uint8_t kFlag_Control   = 0x80;
-
-  const static uint8_t kFlag_Data_FIN  = 0x01;
-  const static uint8_t kFlag_Data_UNI  = 0x02;
-
-  enum
-  {
-    CONTROL_TYPE_FIRST = 0,
-    CONTROL_TYPE_SYN_STREAM = 1,
-    CONTROL_TYPE_SYN_REPLY = 2,
-    CONTROL_TYPE_RST_STREAM = 3,
-    CONTROL_TYPE_SETTINGS = 4,
-    CONTROL_TYPE_NOOP = 5,                        /* deprecated */
-    CONTROL_TYPE_PING = 6,
-    CONTROL_TYPE_GOAWAY = 7,
-    CONTROL_TYPE_HEADERS = 8,
-    CONTROL_TYPE_WINDOW_UPDATE = 9,
-    CONTROL_TYPE_CREDENTIAL = 10,
-    CONTROL_TYPE_LAST = 11
-  };
-
-  enum rstReason
-  {
-    RST_PROTOCOL_ERROR = 1,
-    RST_INVALID_STREAM = 2,
-    RST_REFUSED_STREAM = 3,
-    RST_UNSUPPORTED_VERSION = 4,
-    RST_CANCEL = 5,
-    RST_INTERNAL_ERROR = 6,
-    RST_FLOW_CONTROL_ERROR = 7,
-    RST_STREAM_IN_USE = 8,
-    RST_STREAM_ALREADY_CLOSED = 9,
-    RST_INVALID_CREDENTIALS = 10,
-    RST_FRAME_TOO_LARGE = 11
-  };
-
-  enum goawayReason
-  {
-    OK = 0,
-    PROTOCOL_ERROR = 1,
-    INTERNAL_ERROR = 2,    // sometimes misdocumented as 11
-    NUM_STATUS_CODES = 3   // reserved by chromium but undocumented
-  };
-
-  enum settingsFlags
-  {
-    PERSIST_VALUE = 1,
-    PERSISTED_VALUE = 2
-  };
-
-  enum
-  {
-    SETTINGS_TYPE_UPLOAD_BW = 1, // kb/s
-    SETTINGS_TYPE_DOWNLOAD_BW = 2, // kb/s
-    SETTINGS_TYPE_RTT = 3, // ms
-    SETTINGS_TYPE_MAX_CONCURRENT = 4, // streams
-    SETTINGS_TYPE_CWND = 5, // packets
-    SETTINGS_TYPE_DOWNLOAD_RETRANS_RATE = 6, // percentage
-    SETTINGS_TYPE_INITIAL_WINDOW = 7,  // bytes for flow control
-    SETTINGS_CLIENT_CERTIFICATE_VECTOR_SIZE = 8
-  };
-
-  // This should be big enough to hold all of your control packets,
-  // but if it needs to grow for huge headers it can do so dynamically.
-  // About 1% of responses from SPDY google services seem to be > 1000
-  // with all less than 2000 when compression is enabled.
-  const static uint32_t kDefaultBufferSize = 2048;
-
-  // kDefaultQueueSize must be >= other queue size constants
-  const static uint32_t kDefaultQueueSize =  32768;
-  const static uint32_t kQueueMinimumCleanup = 24576;
-  const static uint32_t kQueueTailRoom    =  4096;
-  const static uint32_t kQueueReserved    =  1024;
-
-  const static uint32_t kMaxStreamID = 0x7800000;
-
-  // This is a sentinel for a deleted stream. It is not a valid
-  // 31 bit stream ID.
-  const static uint32_t kDeadStreamID = 0xffffdead;
-
-  // below the emergency threshold of local window we ack every received
-  // byte. Above that we coalesce bytes into the MinimumToAck size.
-  const static int32_t  kEmergencyWindowThreshold = 1024 * 1024;
-  const static uint32_t kMinimumToAck = 64 * 1024;
-
-  // The default rwin is 64KB unless updated by a settings frame
-  const static uint32_t kDefaultRwin = 64 * 1024;
-
-  static nsresult HandleSynStream(SpdySession31 *);
-  static nsresult HandleSynReply(SpdySession31 *);
-  static nsresult HandleRstStream(SpdySession31 *);
-  static nsresult HandleSettings(SpdySession31 *);
-  static nsresult HandleNoop(SpdySession31 *);
-  static nsresult HandlePing(SpdySession31 *);
-  static nsresult HandleGoAway(SpdySession31 *);
-  static nsresult HandleHeaders(SpdySession31 *);
-  static nsresult HandleWindowUpdate(SpdySession31 *);
-  static nsresult HandleCredential(SpdySession31 *);
-
-  // For writing the SPDY data stream to LOG4
-  static void LogIO(SpdySession31 *, SpdyStream31 *, const char *,
-                    const char *, uint32_t);
-
-  // an overload of nsAHttpConnection
-  void TransactionHasDataToWrite(nsAHttpTransaction *) override;
-
-  // a similar version for SpdyStream31
-  void TransactionHasDataToWrite(SpdyStream31 *);
-
-  // an overload of nsAHttpSegementReader
-  virtual nsresult CommitToSegmentSize(uint32_t size, bool forceCommitment) override;
-  nsresult BufferOutput(const char *, uint32_t, uint32_t *);
-  void     FlushOutputQueue();
-  uint32_t AmountOfOutputBuffered() { return mOutputQueueUsed - mOutputQueueSent; }
-
-  uint32_t GetServerInitialStreamWindow() { return mServerInitialStreamWindow; }
-
-  bool TryToActivate(SpdyStream31 *stream);
-  void ConnectPushedStream(SpdyStream31 *stream);
-  void DecrementConcurrent(SpdyStream31 *stream);
-
-  uint64_t Serial() { return mSerial; }
-
-  void     PrintDiagnostics (nsCString &log) override;
-
-  // Streams need access to these
-  uint32_t SendingChunkSize() { return mSendingChunkSize; }
-  uint32_t PushAllowance() { return mPushAllowance; }
-  z_stream *UpstreamZlib() { return &mUpstreamZlib; }
-  nsISocketTransport *SocketTransport() { return mSocketTransport; }
-  int64_t RemoteSessionWindow() { return mRemoteSessionWindow; }
-  void DecrementRemoteSessionWindow (uint32_t bytes) { mRemoteSessionWindow -= bytes; }
-
-  void SendPing() override;
-
-  bool MaybeReTunnel(nsAHttpTransaction *) override;
-
-  // overload of nsAHttpTransaction
-  nsresult ReadSegmentsAgain(nsAHttpSegmentReader *, uint32_t, uint32_t *, bool *) override final;
-  nsresult WriteSegmentsAgain(nsAHttpSegmentWriter *, uint32_t , uint32_t *, bool *) override final;
-
-private:
-
-  enum stateType {
-    BUFFERING_FRAME_HEADER,
-    BUFFERING_CONTROL_FRAME,
-    PROCESSING_DATA_FRAME,
-    DISCARDING_DATA_FRAME,
-    PROCESSING_COMPLETE_HEADERS,
-    PROCESSING_CONTROL_RST_STREAM
-  };
-
-  nsresult    ResponseHeadersComplete();
-  uint32_t    GetWriteQueueSize();
-  void        ChangeDownstreamState(enum stateType);
-  void        ResetDownstreamState();
-  nsresult    UncompressAndDiscard(uint32_t, uint32_t);
-  void        zlibInit();
-  void        GeneratePing(uint32_t);
-  void        GenerateRstStream(uint32_t, uint32_t);
-  void        GenerateGoAway(uint32_t);
-  void        CleanupStream(SpdyStream31 *, nsresult, rstReason);
-  void        CloseStream(SpdyStream31 *, nsresult);
-  void        GenerateSettings();
-  void        RemoveStreamFromQueues(SpdyStream31 *);
-
-  void        SetWriteCallbacks();
-  void        RealignOutputQueue();
-
-  void        ProcessPending();
-  nsresult    SetInputFrameDataStream(uint32_t);
-  bool        VerifyStream(SpdyStream31 *, uint32_t);
-  void        SetNeedsCleanup();
-
-  void        UpdateLocalRwin(SpdyStream31 *stream, uint32_t bytes);
-  void        UpdateLocalStreamWindow(SpdyStream31 *stream, uint32_t bytes);
-  void        UpdateLocalSessionWindow(uint32_t bytes);
-
-  bool        RoomForMoreConcurrent();
-  void        IncrementConcurrent(SpdyStream31 *stream);
-  void        QueueStream(SpdyStream31 *stream);
-
-  // a wrapper for all calls to the nshttpconnection level segment writer. Used
-  // to track network I/O for timeout purposes
-  nsresult   NetworkRead(nsAHttpSegmentWriter *, char *, uint32_t, uint32_t *);
-
-  void Shutdown();
-
-  // This is intended to be nsHttpConnectionMgr:nsConnectionHandle taken
-  // from the first transaction on this session. That object contains the
-  // pointer to the real network-level nsHttpConnection object.
-  RefPtr<nsAHttpConnection> mConnection;
-
-  // The underlying socket transport object is needed to propogate some events
-  nsISocketTransport         *mSocketTransport;
-
-  // These are temporary state variables to hold the argument to
-  // Read/WriteSegments so it can be accessed by On(read/write)segment
-  // further up the stack.
-  nsAHttpSegmentReader       *mSegmentReader;
-  nsAHttpSegmentWriter       *mSegmentWriter;
-
-  uint32_t          mSendingChunkSize;        /* the transmission chunk size */
-  uint32_t          mNextStreamID;            /* 24 bits */
-  uint32_t          mConcurrentHighWater;     /* max parallelism on session */
-  uint32_t          mPushAllowance;           /* rwin for unmatched pushes */
-
-  stateType         mDownstreamState; /* in frame, between frames, etc..  */
-
-  // Maintain 2 indexes - one by stream ID, one by transaction pointer.
-  // There are also several lists of streams: ready to write, queued due to
-  // max parallelism, streams that need to force a read for push, and the full
-  // set of pushed streams.
-  // The objects are not ref counted - they get destroyed
-  // by the nsClassHashtable implementation when they are removed from
-  // the transaction hash.
-  nsDataHashtable<nsUint32HashKey, SpdyStream31 *>     mStreamIDHash;
-  nsClassHashtable<nsPtrHashKey<nsAHttpTransaction>,
-    SpdyStream31>                                     mStreamTransactionHash;
-
-  nsDeque                                             mReadyForWrite;
-  nsDeque                                             mQueuedStreams;
-  nsDeque                                             mReadyForRead;
-  nsTArray<SpdyPushedStream31 *>                      mPushedStreams;
-
-  // Compression contexts for header transport using deflate.
-  // SPDY compresses only HTTP headers and does not reset zlib in between
-  // frames. Even data that is not associated with a stream (e.g invalid
-  // stream ID) is passed through these contexts to keep the compression
-  // context correct.
-  z_stream            mDownstreamZlib;
-  z_stream            mUpstreamZlib;
-
-  // mInputFrameBuffer is used to store received control packets and the 8 bytes
-  // of header on data packets
-  uint32_t             mInputFrameBufferSize;
-  uint32_t             mInputFrameBufferUsed;
-  UniquePtr<char[]>    mInputFrameBuffer;
-
-  // mInputFrameDataSize/Read are used for tracking the amount of data consumed
-  // in a data frame. the data itself is not buffered in spdy
-  // The frame size is mInputFrameDataSize + the constant 8 byte header
-  uint32_t             mInputFrameDataSize;
-  uint32_t             mInputFrameDataRead;
-  bool                 mInputFrameDataLast; // This frame was marked FIN
-
-  // When a frame has been received that is addressed to a particular stream
-  // (e.g. a data frame after the stream-id has been decoded), this points
-  // to the stream.
-  SpdyStream31          *mInputFrameDataStream;
-
-  // mNeedsCleanup is a state variable to defer cleanup of a closed stream
-  // If needed, It is set in session::OnWriteSegments() and acted on and
-  // cleared when the stack returns to session::WriteSegments(). The stream
-  // cannot be destroyed directly out of OnWriteSegments because
-  // stream::writeSegments() is on the stack at that time.
-  SpdyStream31          *mNeedsCleanup;
-
-  // The CONTROL_TYPE value for a control frame
-  uint32_t             mFrameControlType;
-
-  // This reason code in the last processed RESET frame
-  uint32_t             mDownstreamRstReason;
-
-  // for the conversion of downstream http headers into spdy formatted headers
-  // The data here does not persist between frames
-  nsCString            mFlatHTTPResponseHeaders;
-  uint32_t             mFlatHTTPResponseHeadersOut;
-
-  // when set, the session will go away when it reaches 0 streams. This flag
-  // is set when: the stream IDs are running out (at either the client or the
-  // server), when DontReuse() is called, a RST that is not specific to a
-  // particular stream is received, a GOAWAY frame has been received from
-  // the server.
-  bool                 mShouldGoAway;
-
-  // the session has received a nsAHttpTransaction::Close()  call
-  bool                 mClosed;
-
-  // the session received a GoAway frame with a valid GoAwayID
-  bool                 mCleanShutdown;
-
-  // indicates PROCESSING_COMPLETE_HEADERS state was pushed onto the stack
-  // over an active PROCESSING_DATA_FRAME, which should be restored when
-  // the processed headers are written to the stream
-  bool                 mDataPending;
-
-  // If a GoAway message was received this is the ID of the last valid
-  // stream. 0 otherwise. (0 is never a valid stream id.)
-  uint32_t             mGoAwayID;
-
-  // The limit on number of concurrent streams for this session. Normally it
-  // is basically unlimited, but the SETTINGS control message from the
-  // server might bring it down.
-  uint32_t             mMaxConcurrent;
-
-  // The actual number of concurrent streams at this moment. Generally below
-  // mMaxConcurrent, but the max can be lowered in real time to a value
-  // below the current value
-  uint32_t             mConcurrent;
-
-  // The number of server initiated SYN-STREAMS, tracked for telemetry
-  uint32_t             mServerPushedResources;
-
-  // The server rwin for new streams as determined from a SETTINGS frame
-  uint32_t             mServerInitialStreamWindow;
-
-  // The Local Session window is how much data the server is allowed to send
-  // (across all streams) without getting a window update to stream 0. It is
-  // signed because asynchronous changes via SETTINGS can drive it negative.
-  int64_t              mLocalSessionWindow;
-
-  // The Remote Session Window is how much data the client is allowed to send
-  // (across all streams) without receiving a window update to stream 0. It is
-  // signed because asynchronous changes via SETTINGS can drive it negative.
-  int64_t              mRemoteSessionWindow;
-
-  // This is a output queue of bytes ready to be written to the SSL stream.
-  // When that streams returns WOULD_BLOCK on direct write the bytes get
-  // coalesced together here. This results in larger writes to the SSL layer.
-  // The buffer is not dynamically grown to accomodate stream writes, but
-  // does expand to accept infallible session wide frames like GoAway and RST.
-  uint32_t             mOutputQueueSize;
-  uint32_t             mOutputQueueUsed;
-  uint32_t             mOutputQueueSent;
-  UniquePtr<char[]>    mOutputQueueBuffer;
-
-  PRIntervalTime       mPingThreshold;
-  PRIntervalTime       mLastReadEpoch;     // used for ping timeouts
-  PRIntervalTime       mLastDataReadEpoch; // used for IdleTime()
-  PRIntervalTime       mPingSentEpoch;
-  uint32_t             mNextPingID;
-
-  PRIntervalTime       mPreviousPingThreshold; // backup for the former value
-  bool                 mPreviousUsed;          // true when backup is used
-
-  // used as a temporary buffer while enumerating the stream hash during GoAway
-  nsDeque  mGoAwayStreamsToRestart;
-
-  // Each session gets a unique serial number because the push cache is correlated
-  // by the load group and the serial number can be used as part of the cache key
-  // to make sure streams aren't shared across sessions.
-  uint64_t        mSerial;
-
-private:
-/// connect tunnels
-  void DispatchOnTunnel(nsAHttpTransaction *, nsIInterfaceRequestor *);
-  void CreateTunnel(nsHttpTransaction *, nsHttpConnectionInfo *, nsIInterfaceRequestor *);
-  void RegisterTunnel(SpdyStream31 *);
-  void UnRegisterTunnel(SpdyStream31 *);
-  uint32_t FindTunnelCount(nsHttpConnectionInfo *);
-
-  nsDataHashtable<nsCStringHashKey, uint32_t> mTunnelHash;
-};
-
-} // namespace net
-} // namespace mozilla
-
-#endif // mozilla_net_SpdySession31_h
deleted file mode 100644
--- a/netwerk/protocol/http/SpdyStream31.cpp
+++ /dev/null
@@ -1,1695 +0,0 @@
-/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
-/* vim: set sw=2 ts=8 et tw=80 : */
-/* This Source Code Form is subject to the terms of the Mozilla Public
- * License, v. 2.0. If a copy of the MPL was not distributed with this
- * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
-
-// HttpLog.h should generally be included first
-#include "HttpLog.h"
-
-// Log on level :5, instead of default :4.
-#undef LOG
-#define LOG(args) LOG5(args)
-#undef LOG_ENABLED
-#define LOG_ENABLED() LOG5_ENABLED()
-
-#include "mozilla/Telemetry.h"
-#include "nsAlgorithm.h"
-#include "nsHttp.h"
-#include "nsHttpHandler.h"
-#include "nsHttpRequestHead.h"
-#include "nsISocketTransport.h"
-#include "nsISupportsPriority.h"
-#include "prnetdb.h"
-#include "SpdyPush31.h"
-#include "SpdySession31.h"
-#include "SpdyStream31.h"
-#include "TunnelUtils.h"
-
-#include <algorithm>
-
-namespace mozilla {
-namespace net {
-
-SpdyStream31::SpdyStream31(nsAHttpTransaction *httpTransaction,
-                           SpdySession31 *spdySession,
-                           int32_t priority)
-  : mStreamID(0)
-  , mSession(spdySession)
-  , mUpstreamState(GENERATING_SYN_STREAM)
-  , mRequestHeadersDone(0)
-  , mSynFrameGenerated(0)
-  , mSentFinOnData(0)
-  , mQueued(0)
-  , mTransaction(httpTransaction)
-  , mSocketTransport(spdySession->SocketTransport())
-  , mSegmentReader(nullptr)
-  , mSegmentWriter(nullptr)
-  , mChunkSize(spdySession->SendingChunkSize())
-  , mRequestBlockedOnRead(0)
-  , mRecvdFin(0)
-  , mFullyOpen(0)
-  , mSentWaitingFor(0)
-  , mReceivedData(0)
-  , mSetTCPSocketBuffer(0)
-  , mCountAsActive(0)
-  , mTxInlineFrameSize(SpdySession31::kDefaultBufferSize)
-  , mTxInlineFrameUsed(0)
-  , mTxStreamFrameSize(0)
-  , mZlib(spdySession->UpstreamZlib())
-  , mDecompressBufferSize(SpdySession31::kDefaultBufferSize)
-  , mDecompressBufferUsed(0)
-  , mDecompressedBytes(0)
-  , mRequestBodyLenRemaining(0)
-  , mPriority(priority)
-  , mLocalUnacked(0)
-  , mBlockedOnRwin(false)
-  , mTotalSent(0)
-  , mTotalRead(0)
-  , mPushSource(nullptr)
-  , mIsTunnel(false)
-  , mPlainTextTunnel(false)
-{
-  MOZ_ASSERT(PR_GetCurrentThread() == gSocketThread);
-
-  LOG3(("SpdyStream31::SpdyStream31 %p", this));
-
-  mRemoteWindow = spdySession->GetServerInitialStreamWindow();
-  mLocalWindow = spdySession->PushAllowance();
-
-  mTxInlineFrame = MakeUnique<uint8_t[]>(mTxInlineFrameSize);
-  mDecompressBuffer = MakeUnique<char[]>(mDecompressBufferSize);
-}
-
-SpdyStream31::~SpdyStream31()
-{
-  ClearTransactionsBlockedOnTunnel();
-  mStreamID = SpdySession31::kDeadStreamID;
-}
-
-// ReadSegments() is used to write data down the socket. Generally, HTTP
-// request data is pulled from the approriate transaction and
-// converted to SPDY data. Sometimes control data like a window-update is
-// generated instead.
-
-nsresult
-SpdyStream31::ReadSegments(nsAHttpSegmentReader *reader,
-                           uint32_t count,
-                           uint32_t *countRead)
-{
-  LOG3(("SpdyStream31 %p ReadSegments reader=%p count=%d state=%x",
-        this, reader, count, mUpstreamState));
-
-  MOZ_ASSERT(PR_GetCurrentThread() == gSocketThread);
-
-  nsresult rv = NS_ERROR_UNEXPECTED;
-  mRequestBlockedOnRead = 0;
-
-  // avoid runt chunks if possible by anticipating
-  // full data frames
-  if (count > (mChunkSize + 8)) {
-    uint32_t numchunks = count / (mChunkSize + 8);
-    count = numchunks * (mChunkSize + 8);
-  }
-
-  switch (mUpstreamState) {
-  case GENERATING_SYN_STREAM:
-  case GENERATING_REQUEST_BODY:
-  case SENDING_REQUEST_BODY:
-    // Call into the HTTP Transaction to generate the HTTP request
-    // stream. That stream will show up in OnReadSegment().
-    mSegmentReader = reader;
-    rv = mTransaction->ReadSegments(this, count, countRead);
-    mSegmentReader = nullptr;
-    LOG3(("SpdyStream31::ReadSegments %p trans readsegments rv %x read=%d\n",
-          this, rv, *countRead));
-    // Check to see if the transaction's request could be written out now.
-    // If not, mark the stream for callback when writing can proceed.
-    if (NS_SUCCEEDED(rv) &&
-        mUpstreamState == GENERATING_SYN_STREAM &&
-        !mRequestHeadersDone)
-      mSession->TransactionHasDataToWrite(this);
-
-    // mTxinlineFrameUsed represents any queued un-sent frame. It might
-    // be 0 if there is no such frame, which is not a gurantee that we
-    // don't have more request body to send - just that any data that was
-    // sent comprised a complete SPDY frame. Likewise, a non 0 value is
-    // a queued, but complete, spdy frame length.
-
-    // Mark that we are blocked on read if the http transaction needs to
-    // provide more of the request message body and there is nothing queued
-    // for writing
-    if (rv == NS_BASE_STREAM_WOULD_BLOCK && !mTxInlineFrameUsed)
-      mRequestBlockedOnRead = 1;
-
-    // A transaction that had already generated its headers before it was
-    // queued at the session level (due to concurrency concerns) may not call
-    // onReadSegment off the ReadSegments() stack above.
-    if (mUpstreamState == GENERATING_SYN_STREAM && NS_SUCCEEDED(rv)) {
-      LOG3(("SpdyStream31 %p ReadSegments forcing OnReadSegment call\n", this));
-      uint32_t wasted = 0;
-      mSegmentReader = reader;
-      OnReadSegment("", 0, &wasted);
-      mSegmentReader = nullptr;
-    }
-
-    // If the sending flow control window is open (!mBlockedOnRwin) then
-    // continue sending the request
-    if (!mBlockedOnRwin && mSynFrameGenerated &&
-        !mTxInlineFrameUsed && NS_SUCCEEDED(rv) && (!*countRead)) {
-      LOG3(("SpdyStream31::ReadSegments %p 0x%X: Sending request data complete, "
-            "mUpstreamState=%x finondata=%d",this, mStreamID,
-            mUpstreamState, mSentFinOnData));
-      if (mSentFinOnData) {
-        ChangeState(UPSTREAM_COMPLETE);
-      } else {
-        GenerateDataFrameHeader(0, true);
-        ChangeState(SENDING_FIN_STREAM);
-        mSession->TransactionHasDataToWrite(this);
-        rv = NS_BASE_STREAM_WOULD_BLOCK;
-      }
-    }
-    break;
-
-  case SENDING_FIN_STREAM:
-    // We were trying to send the FIN-STREAM but were blocked from
-    // sending it out - try again.
-    if (!mSentFinOnData) {
-      mSegmentReader = reader;
-      rv = TransmitFrame(nullptr, nullptr, false);
-      mSegmentReader = nullptr;
-      MOZ_ASSERT(NS_FAILED(rv) || !mTxInlineFrameUsed,
-                 "Transmit Frame should be all or nothing");
-      if (NS_SUCCEEDED(rv))
-        ChangeState(UPSTREAM_COMPLETE);
-    }
-    else {
-      rv = NS_OK;
-      mTxInlineFrameUsed = 0;         // cancel fin data packet
-      ChangeState(UPSTREAM_COMPLETE);
-    }
-
-    *countRead = 0;
-
-    // don't change OK to WOULD BLOCK. we are really done sending if OK
-    break;
-
-  case UPSTREAM_COMPLETE:
-    *countRead = 0;
-    rv = NS_OK;
-    break;
-
-  default:
-    MOZ_ASSERT(false, "SpdyStream31::ReadSegments unknown state");
-    break;
-  }
-
-  return rv;
-}
-
-// WriteSegments() is used to read data off the socket. Generally this is
-// just a call through to the associated nsHttpTransaction for this stream
-// for the remaining data bytes indicated by the current DATA frame.
-
-nsresult
-SpdyStream31::WriteSegments(nsAHttpSegmentWriter *writer,
-                            uint32_t count,
-                            uint32_t *countWritten)
-{
-  MOZ_ASSERT(PR_GetCurrentThread() == gSocketThread);
-  MOZ_ASSERT(!mSegmentWriter, "segment writer in progress");
-
-  LOG3(("SpdyStream31::WriteSegments %p count=%d state=%x",
-        this, count, mUpstreamState));
-
-  mSegmentWriter = writer;
-  nsresult rv = mTransaction->WriteSegments(this, count, countWritten);
-  mSegmentWriter = nullptr;
-
-  return rv;
-}
-
-bool
-SpdyStream31::ChannelPipeFull()
-{
-  nsHttpTransaction *trans = mTransaction ? mTransaction->QueryHttpTransaction() : nullptr;
-  return trans ? trans->ChannelPipeFull() : false;
-}
-
-void
-SpdyStream31::CreatePushHashKey(const nsCString &scheme,
-                                const nsCString &hostHeader,
-                                uint64_t serial,
-                                const nsCSubstring &pathInfo,
-                                nsCString &outOrigin,
-                                nsCString &outKey)
-{
-  outOrigin = scheme;
-  outOrigin.AppendLiteral("://");
-  outOrigin.Append(hostHeader);
-
-  outKey = outOrigin;
-  outKey.AppendLiteral("/[spdy3_1.");
-  outKey.AppendInt(serial);
-  outKey.Append(']');
-  outKey.Append(pathInfo);
-}
-
-
-nsresult
-SpdyStream31::ParseHttpRequestHeaders(const char *buf,
-                                      uint32_t avail,
-                                      uint32_t *countUsed)
-{
-  // Returns NS_OK even if the headers are incomplete
-  // set mRequestHeadersDone flag if they are complete
-
-  MOZ_ASSERT(PR_GetCurrentThread() == gSocketThread);
-  MOZ_ASSERT(mUpstreamState == GENERATING_SYN_STREAM);
-  MOZ_ASSERT(!mRequestHeadersDone);
-
-  LOG3(("SpdyStream31::ParseHttpRequestHeaders %p avail=%d state=%x",
-        this, avail, mUpstreamState));
-
-  mFlatHttpRequestHeaders.Append(buf, avail);
-
-  // We can use the simple double crlf because firefox is the
-  // only client we are parsing
-  int32_t endHeader = mFlatHttpRequestHeaders.Find("\r\n\r\n");
-
-  if (endHeader == kNotFound) {
-    // We don't have all the headers yet
-    LOG3(("SpdyStream31::ParseHttpRequestHeaders %p "
-          "Need more header bytes. Len = %d",
-          this, mFlatHttpRequestHeaders.Length()));
-    *countUsed = avail;
-    return NS_OK;
-  }
-
-  // We have recvd all the headers, trim the local
-  // buffer of the final empty line, and set countUsed to reflect
-  // the whole header has been consumed.
-  uint32_t oldLen = mFlatHttpRequestHeaders.Length();
-  mFlatHttpRequestHeaders.SetLength(endHeader + 2);
-  *countUsed = avail - (oldLen - endHeader) + 4;
-  mRequestHeadersDone = 1;
-
-  nsAutoCString hostHeader;
-  nsAutoCString hashkey;
-  mTransaction->RequestHead()->GetHeader(nsHttp::Host, hostHeader);
-  nsAutoCString requestURI;
-  mTransaction->RequestHead()->RequestURI(requestURI);
-  CreatePushHashKey(nsDependentCString(mTransaction->RequestHead()->IsHTTPS() ? "https" : "http"),
-                    hostHeader, mSession->Serial(),
-                    requestURI,
-                    mOrigin, hashkey);
-
-  // check the push cache for GET
-  if (mTransaction->RequestHead()->IsGet()) {
-    // from :scheme, :host, :path
-    nsIRequestContext *requestContext = mTransaction->RequestContext();
-    SpdyPushCache *cache = nullptr;
-    if (requestContext)
-      requestContext->GetSpdyPushCache(&cache);
-
-    SpdyPushedStream31 *pushedStream = nullptr;
-    // we remove the pushedstream from the push cache so that
-    // it will not be used for another GET. This does not destroy the
-    // stream itself - that is done when the transactionhash is done with it.
-    if (cache)
-      pushedStream = cache->RemovePushedStreamSpdy31(hashkey);
-
-    if (pushedStream) {
-      LOG3(("Pushed Stream Match located id=0x%X key=%s\n",
-            pushedStream->StreamID(), hashkey.get()));
-      pushedStream->SetConsumerStream(this);
-      mPushSource = pushedStream;
-      mSentFinOnData = 1;
-
-      // This stream has been activated (and thus counts against the concurrency
-      // limit intentionally), but will not be registered via
-      // RegisterStreamID (below) because of the push match. Therefore the
-      // concurrency sempahore needs to be balanced.
-      mSession->DecrementConcurrent(this);
-
-      // There is probably pushed data buffered so trigger a read manually
-      // as we can't rely on future network events to do it
-      mSession->ConnectPushedStream(this);
-      mSynFrameGenerated = 1;
-      return NS_OK;
-    }
-  }
-  return NS_OK;
-}
-
-nsresult
-SpdyStream31::GenerateSynFrame()
-{
-  // It is now OK to assign a streamID that we are assured will
-  // be monotonically increasing amongst syn-streams on this
-  // session
-  mStreamID = mSession->RegisterStreamID(this);
-  MOZ_ASSERT(mStreamID & 1, "Spdy Stream Channel ID must be odd");
-  MOZ_ASSERT(!mSynFrameGenerated);
-
-  mSynFrameGenerated = 1;
-
-  if (mStreamID >= 0x80000000) {
-    // streamID must fit in 31 bits. This is theoretically possible
-    // because stream ID assignment is asynchronous to stream creation
-    // because of the protocol requirement that the ID in syn-stream
-    // be monotonically increasing. In reality this is really not possible
-    // because new streams stop being added to a session with 0x10000000 / 2
-    // IDs still available and no race condition is going to bridge that gap,
-    // so we can be comfortable on just erroring out for correctness in that
-    // case.
-    LOG3(("Stream assigned out of range ID: 0x%X", mStreamID));
-    return NS_ERROR_UNEXPECTED;
-  }
-
-  // Now we need to convert the flat http headers into a set
-  // of SPDY headers..  writing to mTxInlineFrame{sz}
-
-  mTxInlineFrame[0] = SpdySession31::kFlag_Control;
-  mTxInlineFrame[1] = SpdySession31::kVersion;
-  mTxInlineFrame[2] = 0;
-  mTxInlineFrame[3] = SpdySession31::CONTROL_TYPE_SYN_STREAM;
-  // 4 to 7 are length and flags, we'll fill that in later
-
-  uint32_t networkOrderID = PR_htonl(mStreamID);
-  memcpy(&mTxInlineFrame[8], &networkOrderID, 4);
-
-  // this is the associated-to field, which is not used sending
-  // from the client in the http binding
-  memset (&mTxInlineFrame[12], 0, 4);
-
-  // Priority flags are the E0 mask of byte 16.
-  // 0 is highest priority, 7 is lowest.
-  // The other 5 bits of byte 16 are unused.
-
-  if (mPriority >= nsISupportsPriority::PRIORITY_LOWEST)
-    mTxInlineFrame[16] = 7 << 5;
-  else if (mPriority <= nsISupportsPriority::PRIORITY_HIGHEST)
-    mTxInlineFrame[16] = 0 << 5;
-  else {
-    // The priority mapping relies on the unfiltered ranged to be
-    // between -20 .. +20
-    PR_STATIC_ASSERT(nsISupportsPriority::PRIORITY_LOWEST == 20);
-    PR_STATIC_ASSERT(nsISupportsPriority::PRIORITY_HIGHEST == -20);
-
-    // Add one to the priority so that values such as -10 and -11
-    // get different spdy priorities - this appears to be an important
-    // breaking line in the priorities content assigns to
-    // transactions.
-    uint8_t calculatedPriority = 3 + ((mPriority + 1) / 5);
-    MOZ_ASSERT (!(calculatedPriority & 0xf8),
-                "Calculated Priority Out Of Range");
-    mTxInlineFrame[16] = calculatedPriority << 5;
-  }
-
-  // The client cert "slot". Right now we don't send client certs
-  mTxInlineFrame[17] = 0;
-
-  nsCString versionHeader;
-  if (mTransaction->RequestHead()->Version() == NS_HTTP_VERSION_1_1)
-    versionHeader = NS_LITERAL_CSTRING("HTTP/1.1");
-  else
-    versionHeader = NS_LITERAL_CSTRING("HTTP/1.0");
-
-  // use mRequestHead() to get a sense of how big to make the hash,
-  // even though we are parsing the actual text stream because
-  // it is legit to append headers.
-  nsClassHashtable<nsCStringHashKey, nsCString>
-    hdrHash(mTransaction->RequestHead()->HeaderCount());
-
-  const char *beginBuffer = mFlatHttpRequestHeaders.BeginReading();
-
-  // need to hash all the headers together to remove duplicates, special
-  // headers, etc..
-
-  int32_t crlfIndex = mFlatHttpRequestHeaders.Find("\r\n");
-  while (true) {
-    int32_t startIndex = crlfIndex + 2;
-
-    crlfIndex = mFlatHttpRequestHeaders.Find("\r\n", false, startIndex);
-    if (crlfIndex == -1)
-      break;
-
-    int32_t colonIndex = mFlatHttpRequestHeaders.Find(":", false, startIndex,
-                                                      crlfIndex - startIndex);
-    if (colonIndex == -1)
-      break;
-
-    nsDependentCSubstring name = Substring(beginBuffer + startIndex,
-                                           beginBuffer + colonIndex);
-    // all header names are lower case in spdy
-    ToLowerCase(name);
-
-    // exclusions.. mostly from 3.2.1
-    // we send accept-encoding here because we often include brotli
-    // in that list which is greater than the implied accept-encoding: gzip
-    if (name.EqualsLiteral("connection") ||
-        name.EqualsLiteral("keep-alive") ||
-        name.EqualsLiteral("host") ||
-        name.EqualsLiteral("te") ||
-        name.EqualsLiteral("transfer-encoding"))
-      continue;
-
-    nsCString *val = hdrHash.Get(name);
-    if (!val) {
-      val = new nsCString();
-      hdrHash.Put(name, val);
-    }
-
-    int32_t valueIndex = colonIndex + 1;
-    while (valueIndex < crlfIndex && beginBuffer[valueIndex] == ' ')
-      ++valueIndex;
-
-    nsDependentCSubstring v = Substring(beginBuffer + valueIndex,
-                                        beginBuffer + crlfIndex);
-    if (!val->IsEmpty())
-      val->Append(static_cast<char>(0));
-    val->Append(v);
-
-    if (name.EqualsLiteral("content-length")) {
-      int64_t len;
-      if (nsHttp::ParseInt64(val->get(), nullptr, &len))
-        mRequestBodyLenRemaining = len;
-    }
-  }
-
-  mTxInlineFrameUsed = 18;
-
-  // Do not naively log the request headers here beacuse they might
-  // contain auth. The http transaction already logs the sanitized request
-  // headers at this same level so it is not necessary to do so here.
-
-  nsAutoCString method;
-  mTransaction->RequestHead()->Method(method);
-  LOG3(("Stream method %p 0x%X %s\n", this, mStreamID, method.get()));
-
-  // The header block length
-  uint16_t count = hdrHash.Count() + 4; /* :method, :path, :version, :host */
-  if (mTransaction->RequestHead()->IsConnect()) {
-    mRequestBodyLenRemaining = 0x0fffffffffffffffULL;
-  } else {
-    ++count; // :scheme used if not connect
-  }
-  CompressToFrame(count);
-
-  // :method, :path, :version comprise a HTTP/1 request line, so send those first
-  // to make life easy for any gateways
-  CompressToFrame(NS_LITERAL_CSTRING(":method"));
-  CompressToFrame(method);
-
-  CompressToFrame(NS_LITERAL_CSTRING(":path"));
-  if (!mTransaction->RequestHead()->IsConnect()) {
-    nsAutoCString path;
-    mTransaction->RequestHead()->Path(path);
-    CompressToFrame(path);
-  } else {
-    MOZ_ASSERT(mTransaction->QuerySpdyConnectTransaction());
-    mIsTunnel = true;
-    // Connect places host:port in :path. Don't use default port.
-    nsHttpConnectionInfo *ci = mTransaction->ConnectionInfo();
-    if (!ci) {
-      return NS_ERROR_UNEXPECTED;
-    }
-    nsAutoCString route;
-    route = ci->GetOrigin();
-    route.Append(':');
-    route.AppendInt(ci->OriginPort());
-    CompressToFrame(route);
-  }
-
-  CompressToFrame(NS_LITERAL_CSTRING(":version"));
-  CompressToFrame(versionHeader);
-
-  nsAutoCString hostHeader;
-  mTransaction->RequestHead()->GetHeader(nsHttp::Host, hostHeader);
-  CompressToFrame(NS_LITERAL_CSTRING(":host"));
-  CompressToFrame(hostHeader);
-
-  if (!mTransaction->RequestHead()->IsConnect()) {
-    // no :scheme with connect
-    CompressToFrame(NS_LITERAL_CSTRING(":scheme"));
-    CompressToFrame(nsDependentCString(mTransaction->RequestHead()->IsHTTPS() ? "https" : "http"));
-  }
-
-  for (auto iter = hdrHash.Iter(); !iter.Done(); iter.Next()) {
-    CompressToFrame(iter.Key());
-    CompressToFrame(iter.Data().get());
-  }
-  CompressFlushFrame();
-
-  // 4 to 7 are length and flags, which we can now fill in
-  (reinterpret_cast<uint32_t *>(mTxInlineFrame.get()))[1] =
-    PR_htonl(mTxInlineFrameUsed - 8);
-
-  MOZ_ASSERT(!mTxInlineFrame[4], "Size greater than 24 bits");
-
-  // Determine whether to put the fin bit on the syn stream frame or whether
-  // to wait for a data packet to put it on.
-
-  if (mTransaction->RequestHead()->IsGet() ||
-      mTransaction->RequestHead()->IsHead()) {
-    // for GET and HEAD place the fin bit right on the
-    // syn stream packet
-
-    mSentFinOnData = 1;
-    mTxInlineFrame[4] = SpdySession31::kFlag_Data_FIN;
-  }
-  else if (mTransaction->RequestHead()->IsPost() ||
-           mTransaction->RequestHead()->IsPut() ||
-           mTransaction->RequestHead()->IsConnect() ||
-           mTransaction->RequestHead()->IsOptions()) {
-    // place fin in a data frame even for 0 length messages, I've seen
-    // the google gateway be unhappy with fin-on-syn for 0 length POST
-  }
-  else if (!mRequestBodyLenRemaining) {
-    // for other HTTP extension methods, rely on the content-length
-    // to determine whether or not to put fin on syn
-    mSentFinOnData = 1;
-    mTxInlineFrame[4] = SpdySession31::kFlag_Data_FIN;
-  }
-
-  Telemetry::Accumulate(Telemetry::SPDY_SYN_SIZE, mTxInlineFrameUsed - 18);
-
-  nsAutoCString requestURI;
-  mTransaction->RequestHead()->RequestURI(requestURI);
-  // The size of the input headers is approximate
-  uint32_t ratio =
-    (mTxInlineFrameUsed - 18) * 100 /
-    (11 + requestURI.Length() + mFlatHttpRequestHeaders.Length());
-
-  Telemetry::Accumulate(Telemetry::SPDY_SYN_RATIO, ratio);
-  return NS_OK;
-}
-
-void
-SpdyStream31::AdjustInitialWindow()
-{
-  MOZ_ASSERT(mSession->PushAllowance() <= ASpdySession::kInitialRwin);
-
-  // The session initial_window is sized for serverpushed streams. When we
-  // generate a client pulled stream we want to adjust the initial window
-  // to a huge value in a pipeline with that SYN_STREAM.
-
-  // >0 even numbered IDs are pushed streams.
-  // odd numbered IDs are pulled streams.
-  // 0 is the sink for a pushed stream.
-  SpdyStream31 *stream = this;
-  if (!mStreamID) {
-    MOZ_ASSERT(mPushSource);
-    if (!mPushSource)
-      return;
-    stream = mPushSource;
-    MOZ_ASSERT(stream->mStreamID);
-    MOZ_ASSERT(!(stream->mStreamID & 1)); // is a push stream
-
-    // If the pushed stream has sent a FIN, there is no reason to update
-    // the window
-    if (stream->RecvdFin())
-      return;
-  }
-
-  // For server pushes we also want to include in the ack any data that has been
-  // buffered but unacknowledged.
-
-  // mLocalUnacked is technically 64 bits, but because it can never grow larger than
-  // our window size (which is closer to 29bits max) we know it fits comfortably in 32.
-  // However we don't really enforce that, and track it as a 64 so that broken senders
-  // can still interoperate. That means we have to be careful with this calculation.
-  uint64_t toack64 = (ASpdySession::kInitialRwin - mSession->PushAllowance()) +
-    stream->mLocalUnacked;
-  stream->mLocalUnacked = 0;
-  if (toack64 > 0x7fffffff) {
-    stream->mLocalUnacked = toack64 - 0x7fffffff;
-    toack64 = 0x7fffffff;
-  }
-  uint32_t toack = static_cast<uint32_t>(toack64);
-  if (!toack)
-    return;
-  toack = PR_htonl(toack);
-
-  EnsureBuffer(mTxInlineFrame, mTxInlineFrameUsed + 16,
-               mTxInlineFrameUsed, mTxInlineFrameSize);
-
-  unsigned char *packet = mTxInlineFrame.get() + mTxInlineFrameUsed;
-  mTxInlineFrameUsed += 16;
-
-  memset(packet, 0, 8);
-  packet[0] = SpdySession31::kFlag_Control;
-  packet[1] = SpdySession31::kVersion;
-  packet[3] = SpdySession31::CONTROL_TYPE_WINDOW_UPDATE;
-  packet[7] = 8; // 8 data bytes after 8 byte header
-
-  uint32_t id = PR_htonl(stream->mStreamID);
-  memcpy(packet + 8, &id, 4);
-  memcpy(packet + 12, &toack, 4);
-
-  stream->mLocalWindow += PR_ntohl(toack);
-  LOG3(("AdjustInitialwindow %p 0x%X %u\n",
-        this, stream->mStreamID, PR_ntohl(toack)));
-}
-
-void
-SpdyStream31::UpdateTransportReadEvents(uint32_t count)
-{
-  mTotalRead += count;
-  if (!mSocketTransport) {
-    return;
-  }
-
-  mTransaction->OnTransportStatus(mSocketTransport,
-                                  NS_NET_STATUS_RECEIVING_FROM,
-                                  mTotalRead);
-}
-
-void
-SpdyStream31::UpdateTransportSendEvents(uint32_t count)
-{
-  mTotalSent += count;
-
-  // normally on non-windows platform we use TCP autotuning for
-  // the socket buffers, and this works well (managing enough
-  // buffers for BDP while conserving memory) for HTTP even when
-  // it creates really deep queues. However this 'buffer bloat' is
-  // a problem for spdy because it ruins the low latency properties
-  // necessary for PING and cancel to work meaningfully.
-  //
-  // If this stream represents a large upload, disable autotuning for
-  // the session and cap the send buffers by default at 128KB.
-  // (10Mbit/sec @ 100ms)
-  //
-  uint32_t bufferSize = gHttpHandler->SpdySendBufferSize();
-  if ((mTotalSent > bufferSize) && !mSetTCPSocketBuffer) {
-    mSetTCPSocketBuffer = 1;
-    mSocketTransport->SetSendBufferSize(bufferSize);
-  }
-
-  if (mUpstreamState != SENDING_FIN_STREAM)
-    mTransaction->OnTransportStatus(mSocketTransport,
-                                    NS_NET_STATUS_SENDING_TO,
-                                    mTotalSent);
-
-  if (!mSentWaitingFor && !mRequestBodyLenRemaining) {
-    mSentWaitingFor = 1;
-    mTransaction->OnTransportStatus(mSocketTransport,
-                                    NS_NET_STATUS_WAITING_FOR,
-                                    0);
-  }
-}
-
-nsresult
-SpdyStream31::TransmitFrame(const char *buf,
-                            uint32_t *countUsed,
-                            bool forceCommitment)
-{
-  // If TransmitFrame returns SUCCESS than all the data is sent (or at least
-  // buffered at the session level), if it returns WOULD_BLOCK then none of
-  // the data is sent.
-
-  // You can call this function with no data and no out parameter in order to
-  // flush internal buffers that were previously blocked on writing. You can
-  // of course feed new data to it as well.
-
-  LOG3(("SpdyStream31::TransmitFrame %p inline=%d stream=%d",
-        this, mTxInlineFrameUsed, mTxStreamFrameSize));
-  if (countUsed)
-    *countUsed = 0;
-
-  if (!mTxInlineFrameUsed) {
-    MOZ_ASSERT(!buf);
-    return NS_OK;
-  }
-
-  MOZ_ASSERT(mTxInlineFrameUsed, "empty stream frame in transmit");
-  MOZ_ASSERT(mSegmentReader, "TransmitFrame with null mSegmentReader");
-  MOZ_ASSERT((buf && countUsed) || (!buf && !countUsed),
-             "TransmitFrame arguments inconsistent");
-
-  uint32_t transmittedCount;
-  nsresult rv;
-
-  // In the (relatively common) event that we have a small amount of data
-  // split between the inlineframe and the streamframe, then move the stream
-  // data into the inlineframe via copy in order to coalesce into one write.
-  // Given the interaction with ssl this is worth the small copy cost.
-  if (mTxStreamFrameSize && mTxInlineFrameUsed &&
-      mTxStreamFrameSize < SpdySession31::kDefaultBufferSize &&
-      mTxInlineFrameUsed + mTxStreamFrameSize < mTxInlineFrameSize) {
-    LOG3(("Coalesce Transmit"));
-    memcpy (&mTxInlineFrame[mTxInlineFrameUsed],
-            buf, mTxStreamFrameSize);
-    if (countUsed)
-      *countUsed += mTxStreamFrameSize;
-    mTxInlineFrameUsed += mTxStreamFrameSize;
-    mTxStreamFrameSize = 0;
-  }
-
-  rv =
-    mSegmentReader->CommitToSegmentSize(mTxStreamFrameSize + mTxInlineFrameUsed,
-                                        forceCommitment);
-
-  if (rv == NS_BASE_STREAM_WOULD_BLOCK) {
-    MOZ_ASSERT(!forceCommitment, "forceCommitment with WOULD_BLOCK");
-    mSession->TransactionHasDataToWrite(this);
-  }
-  if (NS_FAILED(rv))     // this will include WOULD_BLOCK
-    return rv;
-
-  // This function calls mSegmentReader->OnReadSegment to report the actual SPDY
-  // bytes through to the SpdySession31 and then the HttpConnection which calls
-  // the socket write function. It will accept all of the inline and stream
-  // data because of the above 'commitment' even if it has to buffer
-
-  rv = mSession->BufferOutput(reinterpret_cast<char*>(mTxInlineFrame.get()),
-                              mTxInlineFrameUsed,
-                              &transmittedCount);
-  LOG3(("SpdyStream31::TransmitFrame for inline BufferOutput session=%p "
-        "stream=%p result %x len=%d",
-        mSession, this, rv, transmittedCount));
-
-  MOZ_ASSERT(rv != NS_BASE_STREAM_WOULD_BLOCK,
-             "inconsistent inline commitment result");
-
-  if (NS_FAILED(rv))
-    return rv;
-
-  MOZ_ASSERT(transmittedCount == mTxInlineFrameUsed,
-             "inconsistent inline commitment count");
-
-  SpdySession31::LogIO(mSession, this, "Writing from Inline Buffer",
-                       reinterpret_cast<char*>(mTxInlineFrame.get()),
-                       transmittedCount);
-
-  if (mTxStreamFrameSize) {
-    if (!buf) {
-      // this cannot happen
-      MOZ_ASSERT(false, "Stream transmit with null buf argument to "
-                 "TransmitFrame()");
-      LOG(("Stream transmit with null buf argument to TransmitFrame()\n"));
-      return NS_ERROR_UNEXPECTED;
-    }
-
-    // If there is already data buffered, just add to that to form
-    // a single TLS Application Data Record - otherwise skip the memcpy
-    if (mSession->AmountOfOutputBuffered()) {
-      rv = mSession->BufferOutput(buf, mTxStreamFrameSize,
-                                  &transmittedCount);
-    } else {
-      rv = mSession->OnReadSegment(buf, mTxStreamFrameSize,
-                                   &transmittedCount);
-    }
-
-    LOG3(("SpdyStream31::TransmitFrame for regular session=%p "
-          "stream=%p result %x len=%d",
-          mSession, this, rv, transmittedCount));
-
-    MOZ_ASSERT(rv != NS_BASE_STREAM_WOULD_BLOCK,
-               "inconsistent stream commitment result");
-
-    if (NS_FAILED(rv))
-      return rv;
-
-    MOZ_ASSERT(transmittedCount == mTxStreamFrameSize,
-               "inconsistent stream commitment count");
-
-    SpdySession31::LogIO(mSession, this, "Writing from Transaction Buffer",
-                         buf, transmittedCount);
-
-    *countUsed += mTxStreamFrameSize;
-  }
-
-  mSession->FlushOutputQueue();
-
-  // calling this will trigger waiting_for if mRequestBodyLenRemaining is 0
-  UpdateTransportSendEvents(mTxInlineFrameUsed + mTxStreamFrameSize);
-
-  mTxInlineFrameUsed = 0;
-  mTxStreamFrameSize = 0;
-
-  return NS_OK;
-}
-
-void
-SpdyStream31::ChangeState(enum stateType newState)
-{
-  LOG3(("SpdyStream31::ChangeState() %p from %X to %X",
-        this, mUpstreamState, newState));
-  mUpstreamState = newState;
-  return;
-}
-
-void
-SpdyStream31::GenerateDataFrameHeader(uint32_t dataLength, bool lastFrame)
-{
-  LOG3(("SpdyStream31::GenerateDataFrameHeader %p len=%d last=%d id=0x%X\n",
-        this, dataLength, lastFrame, mStreamID));
-
-  MOZ_ASSERT(PR_GetCurrentThread() == gSocketThread);
-  MOZ_ASSERT(!mTxInlineFrameUsed, "inline frame not empty");
-  MOZ_ASSERT(!mTxStreamFrameSize, "stream frame not empty");
-  MOZ_ASSERT(!(dataLength & 0xff000000), "datalength > 24 bits");
-  MOZ_ASSERT(mStreamID != 0);
-  MOZ_ASSERT(mStreamID != SpdySession31::kDeadStreamID);
-
-  (reinterpret_cast<uint32_t *>(mTxInlineFrame.get()))[0] = PR_htonl(mStreamID);
-  (reinterpret_cast<uint32_t *>(mTxInlineFrame.get()))[1] =
-    PR_htonl(dataLength);
-
-  MOZ_ASSERT(!(mTxInlineFrame[0] & 0x80), "control bit set unexpectedly");
-  MOZ_ASSERT(!mTxInlineFrame[4], "flag bits set unexpectedly");
-
-  mTxInlineFrameUsed = 8;
-  mTxStreamFrameSize = dataLength;
-
-  if (lastFrame) {
-    mTxInlineFrame[4] |= SpdySession31::kFlag_Data_FIN;
-    if (dataLength)
-      mSentFinOnData = 1;
-  }
-}
-
-void
-SpdyStream31::CompressToFrame(const nsACString &str)
-{
-  CompressToFrame(str.BeginReading(), str.Length());
-}
-
-void
-SpdyStream31::CompressToFrame(const nsACString *str)
-{
-  CompressToFrame(str->BeginReading(), str->Length());
-}
-
-// Dictionary taken from
-// http://dev.chromium.org/spdy/spdy-protocol/spdy-protocol-draft3
-
-const unsigned char SpdyStream31::kDictionary[] = {
-  0x00, 0x00, 0x00, 0x07, 0x6f, 0x70, 0x74, 0x69,   // - - - - o p t i
-  0x6f, 0x6e, 0x73, 0x00, 0x00, 0x00, 0x04, 0x68,   // o n s - - - - h
-  0x65, 0x61, 0x64, 0x00, 0x00, 0x00, 0x04, 0x70,   // e a d - - - - p
-  0x6f, 0x73, 0x74, 0x00, 0x00, 0x00, 0x03, 0x70,   // o s t - - - - p
-  0x75, 0x74, 0x00, 0x00, 0x00, 0x06, 0x64, 0x65,   // u t - - - - d e
-  0x6c, 0x65, 0x74, 0x65, 0x00, 0x00, 0x00, 0x05,   // l e t e - - - -
-  0x74, 0x72, 0x61, 0x63, 0x65, 0x00, 0x00, 0x00,   // t r a c e - - -
-  0x06, 0x61, 0x63, 0x63, 0x65, 0x70, 0x74, 0x00,   // - a c c e p t -
-  0x00, 0x00, 0x0e, 0x61, 0x63, 0x63, 0x65, 0x70,   // - - - a c c e p
-  0x74, 0x2d, 0x63, 0x68, 0x61, 0x72, 0x73, 0x65,   // t - c h a r s e
-  0x74, 0x00, 0x00, 0x00, 0x0f, 0x61, 0x63, 0x63,   // t - - - - a c c
-  0x65, 0x70, 0x74, 0x2d, 0x65, 0x6e, 0x63, 0x6f,   // e p t - e n c o
-  0x64, 0x69, 0x6e, 0x67, 0x00, 0x00, 0x00, 0x0f,   // d i n g - - - -
-  0x61, 0x63, 0x63, 0x65, 0x70, 0x74, 0x2d, 0x6c,   // a c c e p t - l
-  0x61, 0x6e, 0x67, 0x75, 0x61, 0x67, 0x65, 0x00,   // a n g u a g e -
-  0x00, 0x00, 0x0d, 0x61, 0x63, 0x63, 0x65, 0x70,   // - - - a c c e p
-  0x74, 0x2d, 0x72, 0x61, 0x6e, 0x67, 0x65, 0x73,   // t - r a n g e s
-  0x00, 0x00, 0x00, 0x03, 0x61, 0x67, 0x65, 0x00,   // - - - - a g e -
-  0x00, 0x00, 0x05, 0x61, 0x6c, 0x6c, 0x6f, 0x77,   // - - - a l l o w
-  0x00, 0x00, 0x00, 0x0d, 0x61, 0x75, 0x74, 0x68,   // - - - - a u t h
-  0x6f, 0x72, 0x69, 0x7a, 0x61, 0x74, 0x69, 0x6f,   // o r i z a t i o
-  0x6e, 0x00, 0x00, 0x00, 0x0d, 0x63, 0x61, 0x63,   // n - - - - c a c
-  0x68, 0x65, 0x2d, 0x63, 0x6f, 0x6e, 0x74, 0x72,   // h e - c o n t r
-  0x6f, 0x6c, 0x00, 0x00, 0x00, 0x0a, 0x63, 0x6f,   // o l - - - - c o
-  0x6e, 0x6e, 0x65, 0x63, 0x74, 0x69, 0x6f, 0x6e,   // n n e c t i o n
-  0x00, 0x00, 0x00, 0x0c, 0x63, 0x6f, 0x6e, 0x74,   // - - - - c o n t
-  0x65, 0x6e, 0x74, 0x2d, 0x62, 0x61, 0x73, 0x65,   // e n t - b a s e
-  0x00, 0x00, 0x00, 0x10, 0x63, 0x6f, 0x6e, 0x74,   // - - - - c o n t
-  0x65, 0x6e, 0x74, 0x2d, 0x65, 0x6e, 0x63, 0x6f,   // e n t - e n c o
-  0x64, 0x69, 0x6e, 0x67, 0x00, 0x00, 0x00, 0x10,   // d i n g - - - -
-  0x63, 0x6f, 0x6e, 0x74, 0x65, 0x6e, 0x74, 0x2d,   // c o n t e n t -
-  0x6c, 0x61, 0x6e, 0x67, 0x75, 0x61, 0x67, 0x65,   // l a n g u a g e
-  0x00, 0x00, 0x00, 0x0e, 0x63, 0x6f, 0x6e, 0x74,   // - - - - c o n t
-  0x65, 0x6e, 0x74, 0x2d, 0x6c, 0x65, 0x6e, 0x67,   // e n t - l e n g
-  0x74, 0x68, 0x00, 0x00, 0x00, 0x10, 0x63, 0x6f,   // t h - - - - c o
-  0x6e, 0x74, 0x65, 0x6e, 0x74, 0x2d, 0x6c, 0x6f,   // n t e n t - l o
-  0x63, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x00, 0x00,   // c a t i o n - -
-  0x00, 0x0b, 0x63, 0x6f, 0x6e, 0x74, 0x65, 0x6e,   // - - c o n t e n
-  0x74, 0x2d, 0x6d, 0x64, 0x35, 0x00, 0x00, 0x00,   // t - m d 5 - - -
-  0x0d, 0x63, 0x6f, 0x6e, 0x74, 0x65, 0x6e, 0x74,   // - c o n t e n t
-  0x2d, 0x72, 0x61, 0x6e, 0x67, 0x65, 0x00, 0x00,   // - r a n g e - -
-  0x00, 0x0c, 0x63, 0x6f, 0x6e, 0x74, 0x65, 0x6e,   // - - c o n t e n
-  0x74, 0x2d, 0x74, 0x79, 0x70, 0x65, 0x00, 0x00,   // t - t y p e - -
-  0x00, 0x04, 0x64, 0x61, 0x74, 0x65, 0x00, 0x00,   // - - d a t e - -
-  0x00, 0x04, 0x65, 0x74, 0x61, 0x67, 0x00, 0x00,   // - - e t a g - -
-  0x00, 0x06, 0x65, 0x78, 0x70, 0x65, 0x63, 0x74,   // - - e x p e c t
-  0x00, 0x00, 0x00, 0x07, 0x65, 0x78, 0x70, 0x69,   // - - - - e x p i
-  0x72, 0x65, 0x73, 0x00, 0x00, 0x00, 0x04, 0x66,   // r e s - - - - f
-  0x72, 0x6f, 0x6d, 0x00, 0x00, 0x00, 0x04, 0x68,   // r o m - - - - h
-  0x6f, 0x73, 0x74, 0x00, 0x00, 0x00, 0x08, 0x69,   // o s t - - - - i
-  0x66, 0x2d, 0x6d, 0x61, 0x74, 0x63, 0x68, 0x00,   // f - m a t c h -
-  0x00, 0x00, 0x11, 0x69, 0x66, 0x2d, 0x6d, 0x6f,   // - - - i f - m o
-  0x64, 0x69, 0x66, 0x69, 0x65, 0x64, 0x2d, 0x73,   // d i f i e d - s
-  0x69, 0x6e, 0x63, 0x65, 0x00, 0x00, 0x00, 0x0d,   // i n c e - - - -
-  0x69, 0x66, 0x2d, 0x6e, 0x6f, 0x6e, 0x65, 0x2d,   // i f - n o n e -
-  0x6d, 0x61, 0x74, 0x63, 0x68, 0x00, 0x00, 0x00,   // m a t c h - - -
-  0x08, 0x69, 0x66, 0x2d, 0x72, 0x61, 0x6e, 0x67,   // - i f - r a n g
-  0x65, 0x00, 0x00, 0x00, 0x13, 0x69, 0x66, 0x2d,   // e - - - - i f -
-  0x75, 0x6e, 0x6d, 0x6f, 0x64, 0x69, 0x66, 0x69,   // u n m o d i f i
-  0x65, 0x64, 0x2d, 0x73, 0x69, 0x6e, 0x63, 0x65,   // e d - s i n c e
-  0x00, 0x00, 0x00, 0x0d, 0x6c, 0x61, 0x73, 0x74,   // - - - - l a s t
-  0x2d, 0x6d, 0x6f, 0x64, 0x69, 0x66, 0x69, 0x65,   // - m o d i f i e
-  0x64, 0x00, 0x00, 0x00, 0x08, 0x6c, 0x6f, 0x63,   // d - - - - l o c
-  0x61, 0x74, 0x69, 0x6f, 0x6e, 0x00, 0x00, 0x00,   // a t i o n - - -
-  0x0c, 0x6d, 0x61, 0x78, 0x2d, 0x66, 0x6f, 0x72,   // - m a x - f o r
-  0x77, 0x61, 0x72, 0x64, 0x73, 0x00, 0x00, 0x00,   // w a r d s - - -
-  0x06, 0x70, 0x72, 0x61, 0x67, 0x6d, 0x61, 0x00,   // - p r a g m a -
-  0x00, 0x00, 0x12, 0x70, 0x72, 0x6f, 0x78, 0x79,   // - - - p r o x y
-  0x2d, 0x61, 0x75, 0x74, 0x68, 0x65, 0x6e, 0x74,   // - a u t h e n t
-  0x69, 0x63, 0x61, 0x74, 0x65, 0x00, 0x00, 0x00,   // i c a t e - - -
-  0x13, 0x70, 0x72, 0x6f, 0x78, 0x79, 0x2d, 0x61,   // - p r o x y - a
-  0x75, 0x74, 0x68, 0x6f, 0x72, 0x69, 0x7a, 0x61,   // u t h o r i z a
-  0x74, 0x69, 0x6f, 0x6e, 0x00, 0x00, 0x00, 0x05,   // t i o n - - - -
-  0x72, 0x61, 0x6e, 0x67, 0x65, 0x00, 0x00, 0x00,   // r a n g e - - -
-  0x07, 0x72, 0x65, 0x66, 0x65, 0x72, 0x65, 0x72,   // - r e f e r e r
-  0x00, 0x00, 0x00, 0x0b, 0x72, 0x65, 0x74, 0x72,   // - - - - r e t r
-  0x79, 0x2d, 0x61, 0x66, 0x74, 0x65, 0x72, 0x00,   // y - a f t e r -
-  0x00, 0x00, 0x06, 0x73, 0x65, 0x72, 0x76, 0x65,   // - - - s e r v e
-  0x72, 0x00, 0x00, 0x00, 0x02, 0x74, 0x65, 0x00,   // r - - - - t e -
-  0x00, 0x00, 0x07, 0x74, 0x72, 0x61, 0x69, 0x6c,   // - - - t r a i l
-  0x65, 0x72, 0x00, 0x00, 0x00, 0x11, 0x74, 0x72,   // e r - - - - t r
-  0x61, 0x6e, 0x73, 0x66, 0x65, 0x72, 0x2d, 0x65,   // a n s f e r - e
-  0x6e, 0x63, 0x6f, 0x64, 0x69, 0x6e, 0x67, 0x00,   // n c o d i n g -
-  0x00, 0x00, 0x07, 0x75, 0x70, 0x67, 0x72, 0x61,   // - - - u p g r a
-  0x64, 0x65, 0x00, 0x00, 0x00, 0x0a, 0x75, 0x73,   // d e - - - - u s
-  0x65, 0x72, 0x2d, 0x61, 0x67, 0x65, 0x6e, 0x74,   // e r - a g e n t
-  0x00, 0x00, 0x00, 0x04, 0x76, 0x61, 0x72, 0x79,   // - - - - v a r y
-  0x00, 0x00, 0x00, 0x03, 0x76, 0x69, 0x61, 0x00,   // - - - - v i a -
-  0x00, 0x00, 0x07, 0x77, 0x61, 0x72, 0x6e, 0x69,   // - - - w a r n i
-  0x6e, 0x67, 0x00, 0x00, 0x00, 0x10, 0x77, 0x77,   // n g - - - - w w
-  0x77, 0x2d, 0x61, 0x75, 0x74, 0x68, 0x65, 0x6e,   // w - a u t h e n
-  0x74, 0x69, 0x63, 0x61, 0x74, 0x65, 0x00, 0x00,   // t i c a t e - -
-  0x00, 0x06, 0x6d, 0x65, 0x74, 0x68, 0x6f, 0x64,   // - - m e t h o d
-  0x00, 0x00, 0x00, 0x03, 0x67, 0x65, 0x74, 0x00,   // - - - - g e t -
-  0x00, 0x00, 0x06, 0x73, 0x74, 0x61, 0x74, 0x75,   // - - - s t a t u
-  0x73, 0x00, 0x00, 0x00, 0x06, 0x32, 0x30, 0x30,   // s - - - - 2 0 0
-  0x20, 0x4f, 0x4b, 0x00, 0x00, 0x00, 0x07, 0x76,   // - O K - - - - v
-  0x65, 0x72, 0x73, 0x69, 0x6f, 0x6e, 0x00, 0x00,   // e r s i o n - -
-  0x00, 0x08, 0x48, 0x54, 0x54, 0x50, 0x2f, 0x31,   // - - H T T P - 1
-  0x2e, 0x31, 0x00, 0x00, 0x00, 0x03, 0x75, 0x72,   // - 1 - - - - u r
-  0x6c, 0x00, 0x00, 0x00, 0x06, 0x70, 0x75, 0x62,   // l - - - - p u b
-  0x6c, 0x69, 0x63, 0x00, 0x00, 0x00, 0x0a, 0x73,   // l i c - - - - s
-  0x65, 0x74, 0x2d, 0x63, 0x6f, 0x6f, 0x6b, 0x69,   // e t - c o o k i
-  0x65, 0x00, 0x00, 0x00, 0x0a, 0x6b, 0x65, 0x65,   // e - - - - k e e
-  0x70, 0x2d, 0x61, 0x6c, 0x69, 0x76, 0x65, 0x00,   // p - a l i v e -
-  0x00, 0x00, 0x06, 0x6f, 0x72, 0x69, 0x67, 0x69,   // - - - o r i g i
-  0x6e, 0x31, 0x30, 0x30, 0x31, 0x30, 0x31, 0x32,   // n 1 0 0 1 0 1 2
-  0x30, 0x31, 0x32, 0x30, 0x32, 0x32, 0x30, 0x35,   // 0 1 2 0 2 2 0 5
-  0x32, 0x30, 0x36, 0x33, 0x30, 0x30, 0x33, 0x30,   // 2 0 6 3 0 0 3 0
-  0x32, 0x33, 0x30, 0x33, 0x33, 0x30, 0x34, 0x33,   // 2 3 0 3 3 0 4 3
-  0x30, 0x35, 0x33, 0x30, 0x36, 0x33, 0x30, 0x37,   // 0 5 3 0 6 3 0 7
-  0x34, 0x30, 0x32, 0x34, 0x30, 0x35, 0x34, 0x30,   // 4 0 2 4 0 5 4 0
-  0x36, 0x34, 0x30, 0x37, 0x34, 0x30, 0x38, 0x34,   // 6 4 0 7 4 0 8 4
-  0x30, 0x39, 0x34, 0x31, 0x30, 0x34, 0x31, 0x31,   // 0 9 4 1 0 4 1 1
-  0x34, 0x31, 0x32, 0x34, 0x31, 0x33, 0x34, 0x31,   // 4 1 2 4 1 3 4 1
-  0x34, 0x34, 0x31, 0x35, 0x34, 0x31, 0x36, 0x34,   // 4 4 1 5 4 1 6 4
-  0x31, 0x37, 0x35, 0x30, 0x32, 0x35, 0x30, 0x34,   // 1 7 5 0 2 5 0 4
-  0x35, 0x30, 0x35, 0x32, 0x30, 0x33, 0x20, 0x4e,   // 5 0 5 2 0 3 - N
-  0x6f, 0x6e, 0x2d, 0x41, 0x75, 0x74, 0x68, 0x6f,   // o n - A u t h o
-  0x72, 0x69, 0x74, 0x61, 0x74, 0x69, 0x76, 0x65,   // r i t a t i v e
-  0x20, 0x49, 0x6e, 0x66, 0x6f, 0x72, 0x6d, 0x61,   // - I n f o r m a
-  0x74, 0x69, 0x6f, 0x6e, 0x32, 0x30, 0x34, 0x20,   // t i o n 2 0 4 -
-  0x4e, 0x6f, 0x20, 0x43, 0x6f, 0x6e, 0x74, 0x65,   // N o - C o n t e
-  0x6e, 0x74, 0x33, 0x30, 0x31, 0x20, 0x4d, 0x6f,   // n t 3 0 1 - M o
-  0x76, 0x65, 0x64, 0x20, 0x50, 0x65, 0x72, 0x6d,   // v e d - P e r m
-  0x61, 0x6e, 0x65, 0x6e, 0x74, 0x6c, 0x79, 0x34,   // a n e n t l y 4
-  0x30, 0x30, 0x20, 0x42, 0x61, 0x64, 0x20, 0x52,   // 0 0 - B a d - R
-  0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x34, 0x30,   // e q u e s t 4 0
-  0x31, 0x20, 0x55, 0x6e, 0x61, 0x75, 0x74, 0x68,   // 1 - U n a u t h
-  0x6f, 0x72, 0x69, 0x7a, 0x65, 0x64, 0x34, 0x30,   // o r i z e d 4 0
-  0x33, 0x20, 0x46, 0x6f, 0x72, 0x62, 0x69, 0x64,   // 3 - F o r b i d
-  0x64, 0x65, 0x6e, 0x34, 0x30, 0x34, 0x20, 0x4e,   // d e n 4 0 4 - N
-  0x6f, 0x74, 0x20, 0x46, 0x6f, 0x75, 0x6e, 0x64,   // o t - F o u n d
-  0x35, 0x30, 0x30, 0x20, 0x49, 0x6e, 0x74, 0x65,   // 5 0 0 - I n t e
-  0x72, 0x6e, 0x61, 0x6c, 0x20, 0x53, 0x65, 0x72,   // r n a l - S e r
-  0x76, 0x65, 0x72, 0x20, 0x45, 0x72, 0x72, 0x6f,   // v e r - E r r o
-  0x72, 0x35, 0x30, 0x31, 0x20, 0x4e, 0x6f, 0x74,   // r 5 0 1 - N o t
-  0x20, 0x49, 0x6d, 0x70, 0x6c, 0x65, 0x6d, 0x65,   // - I m p l e m e
-  0x6e, 0x74, 0x65, 0x64, 0x35, 0x30, 0x33, 0x20,   // n t e d 5 0 3 -
-  0x53, 0x65, 0x72, 0x76, 0x69, 0x63, 0x65, 0x20,   // S e r v i c e -
-  0x55, 0x6e, 0x61, 0x76, 0x61, 0x69, 0x6c, 0x61,   // U n a v a i l a
-  0x62, 0x6c, 0x65, 0x4a, 0x61, 0x6e, 0x20, 0x46,   // b l e J a n - F
-  0x65, 0x62, 0x20, 0x4d, 0x61, 0x72, 0x20, 0x41,   // e b - M a r - A
-  0x70, 0x72, 0x20, 0x4d, 0x61, 0x79, 0x20, 0x4a,   // p r - M a y - J
-  0x75, 0x6e, 0x20, 0x4a, 0x75, 0x6c, 0x20, 0x41,   // u n - J u l - A
-  0x75, 0x67, 0x20, 0x53, 0x65, 0x70, 0x74, 0x20,   // u g - S e p t -
-  0x4f, 0x63, 0x74, 0x20, 0x4e, 0x6f, 0x76, 0x20,   // O c t - N o v -
-  0x44, 0x65, 0x63, 0x20, 0x30, 0x30, 0x3a, 0x30,   // D e c - 0 0 - 0
-  0x30, 0x3a, 0x30, 0x30, 0x20, 0x4d, 0x6f, 0x6e,   // 0 - 0 0 - M o n
-  0x2c, 0x20, 0x54, 0x75, 0x65, 0x2c, 0x20, 0x57,   // - - T u e - - W
-  0x65, 0x64, 0x2c, 0x20, 0x54, 0x68, 0x75, 0x2c,   // e d - - T h u -
-  0x20, 0x46, 0x72, 0x69, 0x2c, 0x20, 0x53, 0x61,   // - F r i - - S a
-  0x74, 0x2c, 0x20, 0x53, 0x75, 0x6e, 0x2c, 0x20,   // t - - S u n - -
-  0x47, 0x4d, 0x54, 0x63, 0x68, 0x75, 0x6e, 0x6b,   // G M T c h u n k
-  0x65, 0x64, 0x2c, 0x74, 0x65, 0x78, 0x74, 0x2f,   // e d - t e x t -
-  0x68, 0x74, 0x6d, 0x6c, 0x2c, 0x69, 0x6d, 0x61,   // h t m l - i m a
-  0x67, 0x65, 0x2f, 0x70, 0x6e, 0x67, 0x2c, 0x69,   // g e - p n g - i
-  0x6d, 0x61, 0x67, 0x65, 0x2f, 0x6a, 0x70, 0x67,   // m a g e - j p g
-  0x2c, 0x69, 0x6d, 0x61, 0x67, 0x65, 0x2f, 0x67,   // - i m a g e - g
-  0x69, 0x66, 0x2c, 0x61, 0x70, 0x70, 0x6c, 0x69,   // i f - a p p l i
-  0x63, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x2f, 0x78,   // c a t i o n - x
-  0x6d, 0x6c, 0x2c, 0x61, 0x70, 0x70, 0x6c, 0x69,   // m l - a p p l i
-  0x63, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x2f, 0x78,   // c a t i o n - x
-  0x68, 0x74, 0x6d, 0x6c, 0x2b, 0x78, 0x6d, 0x6c,   // h t m l - x m l
-  0x2c, 0x74, 0x65, 0x78, 0x74, 0x2f, 0x70, 0x6c,   // - t e x t - p l
-  0x61, 0x69, 0x6e, 0x2c, 0x74, 0x65, 0x78, 0x74,   // a i n - t e x t
-  0x2f, 0x6a, 0x61, 0x76, 0x61, 0x73, 0x63, 0x72,   // - j a v a s c r
-  0x69, 0x70, 0x74, 0x2c, 0x70, 0x75, 0x62, 0x6c,   // i p t - p u b l
-  0x69, 0x63, 0x70, 0x72, 0x69, 0x76, 0x61, 0x74,   // i c p r i v a t
-  0x65, 0x6d, 0x61, 0x78, 0x2d, 0x61, 0x67, 0x65,   // e m a x - a g e
-  0x3d, 0x67, 0x7a, 0x69, 0x70, 0x2c, 0x64, 0x65,   // - g z i p - d e
-  0x66, 0x6c, 0x61, 0x74, 0x65, 0x2c, 0x73, 0x64,   // f l a t e - s d
-  0x63, 0x68, 0x63, 0x68, 0x61, 0x72, 0x73, 0x65,   // c h c h a r s e
-  0x74, 0x3d, 0x75, 0x74, 0x66, 0x2d, 0x38, 0x63,   // t - u t f - 8 c
-  0x68, 0x61, 0x72, 0x73, 0x65, 0x74, 0x3d, 0x69,   // h a r s e t - i
-  0x73, 0x6f, 0x2d, 0x38, 0x38, 0x35, 0x39, 0x2d,   // s o - 8 8 5 9 -
-  0x31, 0x2c, 0x75, 0x74, 0x66, 0x2d, 0x2c, 0x2a,   // 1 - u t f - - -
-  0x2c, 0x65, 0x6e, 0x71, 0x3d, 0x30, 0x2e          // - e n q - 0 -
-};
-
-// This can be called N times.. 1 for syn_reply and 0->N for headers
-nsresult
-SpdyStream31::Uncompress(z_stream *context,
-                         char *blockStart,
-                         uint32_t blockLen)
-{
-  // ensure the minimum size
-  EnsureBuffer(mDecompressBuffer, SpdySession31::kDefaultBufferSize,
-               mDecompressBufferUsed, mDecompressBufferSize);
-
-  mDecompressedBytes += blockLen;
-
-  context->avail_in = blockLen;
-  context->next_in = reinterpret_cast<unsigned char *>(blockStart);
-  bool triedDictionary = false;
-
-  do {
-    context->next_out =
-      reinterpret_cast<unsigned char *>(mDecompressBuffer.get()) +
-      mDecompressBufferUsed;
-    context->avail_out = mDecompressBufferSize - mDecompressBufferUsed;
-    int zlib_rv = inflate(context, Z_NO_FLUSH);
-    LOG3(("SpdyStream31::Uncompress %p zlib_rv %d\n", this, zlib_rv));
-
-    if (zlib_rv == Z_NEED_DICT) {
-      if (triedDictionary) {
-        LOG3(("SpdyStream31::Uncompress %p Dictionary Error\n", this));
-        return NS_ERROR_ILLEGAL_VALUE;
-      }
-
-      triedDictionary = true;
-      inflateSetDictionary(context, kDictionary, sizeof(kDictionary));
-    } else if (zlib_rv == Z_DATA_ERROR) {
-      LOG3(("SpdyStream31::Uncompress %p inflate returned data err\n", this));
-      return NS_ERROR_ILLEGAL_VALUE;
-    } else  if (zlib_rv < Z_OK) { // probably Z_MEM_ERROR
-      LOG3(("SpdyStream31::Uncompress %p inflate returned %d\n", this, zlib_rv));
-      return NS_ERROR_FAILURE;
-    }
-
-    // zlib's inflate() decreases context->avail_out by the amount it places
-    // in the output buffer
-
-    mDecompressBufferUsed += mDecompressBufferSize - mDecompressBufferUsed -
-      context->avail_out;
-
-    // When there is no more output room, but input still available then
-    // increase the output space
-    if (zlib_rv == Z_OK &&
-        !context->avail_out && context->avail_in) {
-      LOG3(("SpdyStream31::Uncompress %p Large Headers - so far %d",
-            this, mDecompressBufferSize));
-      EnsureBuffer(mDecompressBuffer, mDecompressBufferSize + 4096,
-                   mDecompressBufferUsed, mDecompressBufferSize);
-    }
-  }
-  while (context->avail_in);
-  return NS_OK;
-}
-
-// mDecompressBuffer contains 0 to N uncompressed Name/Value Header blocks
-nsresult
-SpdyStream31::FindHeader(nsCString name,
-                         nsDependentCSubstring &value)
-{
-  const unsigned char *nvpair = reinterpret_cast<unsigned char *>
-    (mDecompressBuffer.get()) + 4;
-  const unsigned char *lastHeaderByte = reinterpret_cast<unsigned char *>
-    (mDecompressBuffer.get()) + mDecompressBufferUsed;
-  if (lastHeaderByte < nvpair)
-    return NS_ERROR_ILLEGAL_VALUE;
-
-  do {
-    uint32_t numPairs = PR_ntohl(reinterpret_cast<const uint32_t *>(nvpair)[-1]);
-
-    for (uint32_t index = 0; index < numPairs; ++index) {
-      if (lastHeaderByte < nvpair + 4)
-        return NS_ERROR_ILLEGAL_VALUE;
-      uint32_t nameLen = (nvpair[0] << 24) + (nvpair[1] << 16) +
-        (nvpair[2] << 8) + nvpair[3];
-      if (lastHeaderByte < nvpair + 4 + nameLen)
-        return NS_ERROR_ILLEGAL_VALUE;
-      nsDependentCSubstring nameString =
-        Substring(reinterpret_cast<const char *>(nvpair) + 4,
-                  reinterpret_cast<const char *>(nvpair) + 4 + nameLen);
-      if (lastHeaderByte < nvpair + 8 + nameLen)
-        return NS_ERROR_ILLEGAL_VALUE;
-      uint32_t valueLen = (nvpair[4 + nameLen] << 24) + (nvpair[5 + nameLen] << 16) +
-        (nvpair[6 + nameLen] << 8) + nvpair[7 + nameLen];
-      if (lastHeaderByte < nvpair + 8 + nameLen + valueLen)
-        return NS_ERROR_ILLEGAL_VALUE;
-      if (nameString.Equals(name)) {
-        value.Assign(((char *)nvpair) + 8 + nameLen, valueLen);
-        return NS_OK;
-      }
-
-      // that pair didn't match - try the next one in this block
-      nvpair += 8 + nameLen + valueLen;
-    }
-
-    // move to the next name/value header block (if there is one) - the
-    // first pair is offset 4 bytes into it
-    nvpair += 4;
-  } while (lastHeaderByte >= nvpair);
-
-  return NS_ERROR_NOT_AVAILABLE;
-}
-
-// ConvertHeaders is used to convert the response headers
-// in a syn_reply or in 0..N headers frames that follow it into
-// HTTP/1 format
-nsresult
-SpdyStream31::ConvertHeaders(nsACString &aHeadersOut)
-{
-  LOG3(("SpdyStream31::ConvertHeaders session=%p stream=%p id=0x%x\n",
-        mSession, this, mStreamID));
-
-  // :status and :version are required.
-  nsDependentCSubstring status, version;
-  nsresult rv = FindHeader(NS_LITERAL_CSTRING(":status"),
-                           status);
-  if (NS_FAILED(rv)) {
-    LOG3(("SpdyStream31::ConvertHeaders session=%p stream=%p id=0x%x missing :status\n",
-          mSession, this, mStreamID));
-    return (rv == NS_ERROR_NOT_AVAILABLE) ? NS_ERROR_ILLEGAL_VALUE : rv;
-  }
-
-  rv = FindHeader(NS_LITERAL_CSTRING(":version"),
-                  version);
-  if (NS_FAILED(rv)) {
-    LOG3(("SpdyStream31::ConvertHeaders session=%p stream=%p id=0x%x missing :version\n",
-          mSession, this, mStreamID));
-    return (rv == NS_ERROR_NOT_AVAILABLE) ? NS_ERROR_ILLEGAL_VALUE : rv;
-  }
-
-  if (mDecompressedBytes && mDecompressBufferUsed) {
-    Telemetry::Accumulate(Telemetry::SPDY_SYN_REPLY_SIZE, mDecompressedBytes);
-    uint32_t ratio =
-      mDecompressedBytes * 100 / mDecompressBufferUsed;
-    Telemetry::Accumulate(Telemetry::SPDY_SYN_REPLY_RATIO, ratio);
-  }
-
-  aHeadersOut.Truncate();
-  aHeadersOut.SetCapacity(mDecompressBufferUsed + 64);
-
-  // Connection, Keep-Alive and chunked transfer encodings are to be
-  // removed.
-
-  // Content-Length is 'advisory'.. we will not strip it because it can
-  // create UI feedback.
-
-  aHeadersOut.Append(version);
-  aHeadersOut.Append(' ');
-  aHeadersOut.Append(status);
-  aHeadersOut.AppendLiteral("\r\n");
-
-  LOG3(("SpdyStream31::ConvertHeaders session=%p stream=%p id=0x%x decompressed size %d\n",
-        mSession, this, mStreamID, mDecompressBufferUsed));
-
-  const unsigned char *nvpair = reinterpret_cast<unsigned char *>
-    (mDecompressBuffer.get()) + 4;
-  const unsigned char *lastHeaderByte = reinterpret_cast<unsigned char *>
-    (mDecompressBuffer.get()) + mDecompressBufferUsed;
-  if (lastHeaderByte < nvpair) {
-    LOG3(("SpdyStream31::ConvertHeaders session=%p stream=%p id=0x%x format err 1\n",
-          mSession, this, mStreamID));
-    return NS_ERROR_ILLEGAL_VALUE;
-  }
-
-  do {
-    uint32_t numPairs = PR_ntohl(reinterpret_cast<const uint32_t *>(nvpair)[-1]);
-    LOG3(("SpdyStream31::ConvertHeaders session=%p stream=%p id=0x%x numPairs %d\n",
-          mSession, this, mStreamID, numPairs));
-
-    for (uint32_t index = 0; index < numPairs; ++index) {
-      LOG5(("SpdyStream31::ConvertHeaders session=%p stream=%p id=0x%x index=%u remaining=%u\n",
-            mSession, this, mStreamID, index, lastHeaderByte - nvpair));
-      if (lastHeaderByte < nvpair + 4) {
-        LOG3(("SpdyStream31::ConvertHeaders session=%p stream=%p id=0x%x format err 2\n",
-              mSession, this, mStreamID));
-        return NS_ERROR_ILLEGAL_VALUE;
-      }
-      uint32_t nameLen = (nvpair[0] << 24) + (nvpair[1] << 16) +
-        (nvpair[2] << 8) + nvpair[3];
-      LOG5(("SpdyStream31::ConvertHeaders session=%p stream=%p id=0x%x namelen=%u\n",
-            mSession, this, mStreamID, nameLen));
-      if (lastHeaderByte < nvpair + 4 + nameLen) {
-        LOG3(("SpdyStream31::ConvertHeaders session=%p stream=%p id=0x%x format err 3\n",
-              mSession, this, mStreamID));
-        return NS_ERROR_ILLEGAL_VALUE;
-      }
-
-      nsDependentCSubstring nameString =
-        Substring(reinterpret_cast<const char *>(nvpair) + 4,
-                  reinterpret_cast<const char *>(nvpair) + 4 + nameLen);
-
-      if (lastHeaderByte < nvpair + 8 + nameLen) {
-        LOG3(("SpdyStream31::ConvertHeaders session=%p stream=%p id=0x%x format err 4\n",
-              mSession, this, mStreamID));
-        return NS_ERROR_ILLEGAL_VALUE;
-      }
-
-      // Look for illegal characters in the nameString.
-      // This includes upper case characters and nulls (as they will
-      // break the fixup-nulls-in-value-string algorithm)
-      // Look for upper case characters in the name. They are illegal.
-      for (char *cPtr = nameString.BeginWriting();
-           cPtr && cPtr < nameString.EndWriting();
-           ++cPtr) {
-        if (*cPtr <= 'Z' && *cPtr >= 'A') {
-          nsCString toLog(nameString);
-
-          LOG3(("SpdyStream31::ConvertHeaders session=%p stream=%p "
-                "upper case response header found. [%s]\n",
-                mSession, this, toLog.get()));
-
-          return NS_ERROR_ILLEGAL_VALUE;
-        }
-
-        // check for null characters
-        if (*cPtr == '\0') {
-          LOG3(("SpdyStream31::ConvertHeaders session=%p stream=%p id=0x%x unexpected null\n",
-                mSession, this, mStreamID));
-          return NS_ERROR_ILLEGAL_VALUE;
-        }
-      }
-
-      // HTTP Chunked responses are not legal over spdy. We do not need
-      // to look for chunked specifically because it is the only HTTP
-      // allowed default encoding and we did not negotiate further encodings
-      // via TE
-      if (nameString.EqualsLiteral("transfer-encoding")) {
-        LOG3(("SpdyStream31::ConvertHeaders session=%p stream=%p "
-              "transfer-encoding found. Chunked is invalid and no TE sent.",
-              mSession, this));
-
-        return NS_ERROR_ILLEGAL_VALUE;
-      }
-
-      uint32_t valueLen =
-        (nvpair[4 + nameLen] << 24) + (nvpair[5 + nameLen] << 16) +
-        (nvpair[6 + nameLen] << 8)  +   nvpair[7 + nameLen];
-      LOG5(("SpdyStream31::ConvertHeaders session=%p stream=%p id=0x%x valueLen=%u\n",
-            mSession, this, mStreamID, valueLen));
-      if (lastHeaderByte < nvpair + 8 + nameLen + valueLen) {
-        LOG3(("SpdyStream31::ConvertHeaders session=%p stream=%p id=0x%x format err 5\n",
-              mSession, this, mStreamID));
-        return NS_ERROR_ILLEGAL_VALUE;
-      }
-
-      // spdy transport level headers shouldn't be gatewayed into http/1
-      if (!nameString.IsEmpty() && nameString[0] != ':' &&
-          !nameString.EqualsLiteral("connection") &&
-          !nameString.EqualsLiteral("keep-alive")) {
-        nsDependentCSubstring valueString =
-          Substring(reinterpret_cast<const char *>(nvpair) + 8 + nameLen,
-                    reinterpret_cast<const char *>(nvpair) + 8 + nameLen +
-                    valueLen);
-
-        aHeadersOut.Append(nameString);
-        aHeadersOut.AppendLiteral(": ");
-
-        // expand NULL bytes in the value string
-        for (char *cPtr = valueString.BeginWriting();
-             cPtr && cPtr < valueString.EndWriting();
-             ++cPtr) {
-          if (*cPtr != 0) {
-            aHeadersOut.Append(*cPtr);
-            continue;
-          }
-
-          // NULLs are really "\r\nhdr: "
-          aHeadersOut.AppendLiteral("\r\n");
-          aHeadersOut.Append(nameString);
-          aHeadersOut.AppendLiteral(": ");
-        }
-
-        aHeadersOut.AppendLiteral("\r\n");
-      }
-      // move to the next name/value pair in this block
-      nvpair += 8 + nameLen + valueLen;
-    }
-
-    // move to the next name/value header block (if there is one) - the
-    // first pair is offset 4 bytes into it
-    nvpair += 4;
-  } while (lastHeaderByte >= nvpair);
-
-  // The decoding went ok. Now we can customize and clean up.
-
-  aHeadersOut.AppendLiteral("X-Firefox-Spdy: 3.1\r\n\r\n");
-  LOG (("decoded response headers are:\n%s",
-        aHeadersOut.BeginReading()));
-
-  // The spdy formatted buffer isnt needed anymore - free it up
-  mDecompressBuffer = nullptr;
-  mDecompressBufferSize = 0;
-  mDecompressBufferUsed = 0;
-
-  if (mIsTunnel && !mPlainTextTunnel) {
-    aHeadersOut.Truncate();
-    LOG(("SpdyStream31::ConvertHeaders %p 0x%X headers removed for tunnel\n",
-         this, mStreamID));
-  }
-
-  return NS_OK;
-}
-
-void
-SpdyStream31::ExecuteCompress(uint32_t flushMode)
-{
-  // Expect mZlib->avail_in and mZlib->next_in to be set.
-  // Append the compressed version of next_in to mTxInlineFrame
-
-  do
-  {
-    uint32_t avail = mTxInlineFrameSize - mTxInlineFrameUsed;
-    if (avail < 1) {
-      EnsureBuffer(mTxInlineFrame, mTxInlineFrameSize + 2000,
-                   mTxInlineFrameUsed, mTxInlineFrameSize);
-      avail = mTxInlineFrameSize - mTxInlineFrameUsed;
-    }
-
-    mZlib->next_out = &mTxInlineFrame[mTxInlineFrameUsed];
-    mZlib->avail_out = avail;
-    deflate(mZlib, flushMode);
-    mTxInlineFrameUsed += avail - mZlib->avail_out;
-  } while (mZlib->avail_in > 0 || !mZlib->avail_out);
-}
-
-void
-SpdyStream31::CompressToFrame(uint32_t data)
-{
-  // convert the data to 4 byte network byte order and write that
-  // to the compressed stream
-  data = PR_htonl(data);
-
-  mZlib->next_in = reinterpret_cast<unsigned char *> (&data);
-  mZlib->avail_in = 4;
-  ExecuteCompress(Z_NO_FLUSH);
-}
-
-
-void
-SpdyStream31::CompressToFrame(const char *data, uint32_t len)
-{
-  // Format calls for a network ordered 32 bit length
-  // followed by the utf8 string
-
-  uint32_t networkLen = PR_htonl(len);
-
-  // write out the length
-  mZlib->next_in = reinterpret_cast<unsigned char *> (&networkLen);
-  mZlib->avail_in = 4;
-  ExecuteCompress(Z_NO_FLUSH);
-
-  // write out the data
-  mZlib->next_in = (unsigned char *)data;
-  mZlib->avail_in = len;
-  ExecuteCompress(Z_NO_FLUSH);
-}
-
-void
-SpdyStream31::CompressFlushFrame()
-{
-  mZlib->next_in = (unsigned char *) "";
-  mZlib->avail_in = 0;
-  ExecuteCompress(Z_SYNC_FLUSH);
-}
-
-bool
-SpdyStream31::GetFullyOpen()
-{
-  return mFullyOpen;
-}
-
-nsresult
-SpdyStream31::SetFullyOpen()
-{
-  MOZ_ASSERT(!mFullyOpen);
-  mFullyOpen = 1;
-  if (mIsTunnel) {
-    int32_t code = 0;
-    nsDependentCSubstring statusSubstring;
-    nsresult rv = FindHeader(NS_LITERAL_CSTRING(":status"), statusSubstring);
-    if (NS_SUCCEEDED(rv)) {
-      nsCString status(statusSubstring);
-      nsresult errcode;
-      code = status.ToInteger(&errcode);
-    }
-
-    LOG3(("SpdyStream31::SetFullyOpen %p Tunnel Response code %d", this, code));
-    if ((code / 100) != 2) {
-      MapStreamToPlainText();
-    }
-
-    MapStreamToHttpConnection();
-    ClearTransactionsBlockedOnTunnel();
-  }
-  return NS_OK;
-}
-
-void
-SpdyStream31::Close(nsresult reason)
-{
-  mTransaction->Close(reason);
-}
-
-void
-SpdyStream31::SetResponseIsComplete()
-{
-  nsHttpTransaction *trans = mTransaction->QueryHttpTransaction();
-  if (trans) {
-    trans->SetResponseIsComplete();
-  }
-}
-
-void
-SpdyStream31::UpdateRemoteWindow(int32_t delta)
-{
-  mRemoteWindow += delta;
-
-  // If the stream had a <=0 window, that has now opened
-  // schedule it for writing again
-  if (mBlockedOnRwin && mSession->RemoteSessionWindow() > 0 &&
-      mRemoteWindow > 0) {
-    // the window has been opened :)
-    mSession->TransactionHasDataToWrite(this);
-  }
-}
-
-//-----------------------------------------------------------------------------
-// nsAHttpSegmentReader
-//-----------------------------------------------------------------------------
-
-nsresult
-SpdyStream31::OnReadSegment(const char *buf,
-                            uint32_t count,
-                            uint32_t *countRead)
-{
-  LOG3(("SpdyStream31::OnReadSegment %p count=%d state=%x",
-        this, count, mUpstreamState));
-
-  MOZ_ASSERT(PR_GetCurrentThread() == gSocketThread);
-  MOZ_ASSERT(mSegmentReader, "OnReadSegment with null mSegmentReader");
-
-  nsresult rv = NS_ERROR_UNEXPECTED;
-  uint32_t dataLength;
-
-  switch (mUpstreamState) {
-  case GENERATING_SYN_STREAM:
-    // The buffer is the HTTP request stream, including at least part of the
-    // HTTP request header. This state's job is to build a SYN_STREAM frame
-    // from the header information. count is the number of http bytes available
-    // (which may include more than the header), and in countRead we return
-    // the number of those bytes that we consume (i.e. the portion that are
-    // header bytes)
-
-    if (!mRequestHeadersDone) {
-      if (NS_FAILED(rv = ParseHttpRequestHeaders(buf, count, countRead))) {
-        return rv;
-      }
-    }
-
-    if (mRequestHeadersDone && !mSynFrameGenerated) {
-      if (!mSession->TryToActivate(this)) {
-        LOG3(("SpdyStream31::OnReadSegment %p cannot activate now. queued.\n", this));
-        return *countRead ? NS_OK : NS_BASE_STREAM_WOULD_BLOCK;
-      }
-      if (NS_FAILED(rv = GenerateSynFrame())) {
-        return rv;
-      }
-    }
-
-    LOG3(("ParseHttpRequestHeaders %p used %d of %d. "
-          "requestheadersdone = %d mSynFrameGenerated = %d\n",
-          this, *countRead, count, mRequestHeadersDone, mSynFrameGenerated));
-    if (mSynFrameGenerated) {
-      AdjustInitialWindow();
-      rv = TransmitFrame(nullptr, nullptr, true);
-      if (rv == NS_BASE_STREAM_WOULD_BLOCK) {
-        // this can't happen
-        MOZ_ASSERT(false, "Transmit Frame SYN_FRAME must at least buffer data");
-        rv = NS_ERROR_UNEXPECTED;
-      }
-
-      ChangeState(GENERATING_REQUEST_BODY);
-      break;
-    }
-    MOZ_ASSERT(*countRead == count, "Header parsing not complete but unused data");
-    break;
-
-  case GENERATING_REQUEST_BODY:
-    if ((mRemoteWindow <= 0) || (mSession->RemoteSessionWindow() <= 0)) {
-      *countRead = 0;
-      LOG3(("SpdyStream31 this=%p, id 0x%X request body suspended because "
-            "remote window is stream=%ld session=%ld.\n", this, mStreamID,
-            mRemoteWindow, mSession->RemoteSessionWindow()));
-      mBlockedOnRwin = true;
-      return NS_BASE_STREAM_WOULD_BLOCK;
-    }
-    mBlockedOnRwin = false;
-
-    dataLength = std::min(count, mChunkSize);
-
-    if (dataLength > mRemoteWindow)
-      dataLength = static_cast<uint32_t>(mRemoteWindow);
-
-    if (dataLength > mSession->RemoteSessionWindow())
-      dataLength = static_cast<uint32_t>(mSession->RemoteSessionWindow());
-
-    LOG3(("SpdyStream31 this=%p id 0x%X remote window is stream %" PRId64 " and "
-          "session %" PRId64". Chunk is %u\n",
-          this, mStreamID, mRemoteWindow,
-          mSession->RemoteSessionWindow(), dataLength));
-    mRemoteWindow -= dataLength;
-    mSession->DecrementRemoteSessionWindow(dataLength);
-
-    LOG3(("SpdyStream31 %p id 0x%x request len remaining %" PRId64 ", "
-          "count avail %u, chunk used %u",
-          this, mStreamID, mRequestBodyLenRemaining, count, dataLength));
-    if (!dataLength && mRequestBodyLenRemaining) {
-      return NS_BASE_STREAM_WOULD_BLOCK;
-    }
-    if (dataLength > mRequestBodyLenRemaining) {
-      return NS_ERROR_UNEXPECTED;
-    }
-    mRequestBodyLenRemaining -= dataLength;
-    GenerateDataFrameHeader(dataLength, !mRequestBodyLenRemaining);
-    ChangeState(SENDING_REQUEST_BODY);
-    MOZ_FALLTHROUGH;
-
-  case SENDING_REQUEST_BODY:
-    MOZ_ASSERT(mTxInlineFrameUsed, "OnReadSegment Send Data Header 0b");
-    rv = TransmitFrame(buf, countRead, false);
-    MOZ_ASSERT(NS_FAILED(rv) || !mTxInlineFrameUsed,
-               "Transmit Frame should be all or nothing");
-
-    LOG3(("TransmitFrame() rv=%x returning %d data bytes. "
-          "Header is %d Body is %d.",
-          rv, *countRead, mTxInlineFrameUsed, mTxStreamFrameSize));
-
-    // normalize a partial write with a WOULD_BLOCK into just a partial write
-    // as some code will take WOULD_BLOCK to mean an error with nothing
-    // written (e.g. nsHttpTransaction::ReadRequestSegment()
-    if (rv == NS_BASE_STREAM_WOULD_BLOCK && *countRead)
-      rv = NS_OK;
-
-    // If that frame was all sent, look for another one
-    if (!mTxInlineFrameUsed)
-      ChangeState(GENERATING_REQUEST_BODY);
-    break;
-
-  case SENDING_FIN_STREAM:
-    MOZ_ASSERT(false, "resuming partial fin stream out of OnReadSegment");
-    break;
-
-  default:
-    MOZ_ASSERT(false, "SpdyStream31::OnReadSegment non-write state");
-    break;
-  }
-
-  return rv;
-}
-
-//-----------------------------------------------------------------------------
-// nsAHttpSegmentWriter
-//-----------------------------------------------------------------------------
-
-nsresult
-SpdyStream31::OnWriteSegment(char *buf,
-                             uint32_t count,
-                             uint32_t *countWritten)
-{
-  LOG3(("SpdyStream31::OnWriteSegment %p count=%d state=%x 0x%X\n",
-        this, count, mUpstreamState, mStreamID));
-
-  MOZ_ASSERT(PR_GetCurrentThread() == gSocketThread);
-  MOZ_ASSERT(mSegmentWriter);
-
-  if (!mPushSource)
-    return mSegmentWriter->OnWriteSegment(buf, count, countWritten);
-
-  nsresult rv;
-  rv = mPushSource->GetBufferedData(buf, count, countWritten);
-  if (NS_FAILED(rv))
-    return rv;
-
-  mSession->ConnectPushedStream(this);
-  return NS_OK;
-}
-
-/// connect tunnels
-
-void
-SpdyStream31::ClearTransactionsBlockedOnTunnel()
-{
-  MOZ_ASSERT(PR_GetCurrentThread() == gSocketThread);
-
-  if (!mIsTunnel) {
-    return;
-  }
-  gHttpHandler->ConnMgr()->ProcessPendingQ(mTransaction->ConnectionInfo());
-}
-
-void
-SpdyStream31::MapStreamToPlainText()
-{
-  RefPtr<SpdyConnectTransaction> qiTrans(mTransaction->QuerySpdyConnectTransaction());
-  MOZ_ASSERT(qiTrans);
-  mPlainTextTunnel = true;
-  qiTrans->ForcePlainText();
-}
-
-void
-SpdyStream31::MapStreamToHttpConnection()
-{
-  RefPtr<SpdyConnectTransaction> qiTrans(mTransaction->QuerySpdyConnectTransaction());
-  MOZ_ASSERT(qiTrans);
-  qiTrans->MapStreamToHttpConnection(mSocketTransport,
-                                     mTransaction->ConnectionInfo());
-}
-
-} // namespace net
-} // namespace mozilla
deleted file mode 100644
--- a/netwerk/protocol/http/SpdyStream31.h
+++ /dev/null
@@ -1,282 +0,0 @@
-/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
-/* This Source Code Form is subject to the terms of the Mozilla Public
- * License, v. 2.0. If a copy of the MPL was not distributed with this
- * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
-
-#ifndef mozilla_net_SpdyStream31_h
-#define mozilla_net_SpdyStream31_h
-
-#include "mozilla/Attributes.h"
-#include "mozilla/UniquePtr.h"
-#include "nsAHttpTransaction.h"
-
-namespace mozilla { namespace net {
-
-class SpdyStream31 : public nsAHttpSegmentReader
-                   , public nsAHttpSegmentWriter
-{
-public:
-  NS_DECL_NSAHTTPSEGMENTREADER
-  NS_DECL_NSAHTTPSEGMENTWRITER
-
-  SpdyStream31(nsAHttpTransaction *, SpdySession31 *, int32_t);
-
-  uint32_t StreamID() { return mStreamID; }
-  SpdyPushedStream31 *PushSource() { return mPushSource; }
-
-  virtual nsresult ReadSegments(nsAHttpSegmentReader *,  uint32_t, uint32_t *);
-  virtual nsresult WriteSegments(nsAHttpSegmentWriter *, uint32_t, uint32_t *);
-  virtual bool DeferCleanupOnSuccess() { return false; }
-
-  const nsAFlatCString &Origin()   const { return mOrigin; }
-
-  bool RequestBlockedOnRead()
-  {
-    return static_cast<bool>(mRequestBlockedOnRead);
-  }
-
-  bool GetFullyOpen();
-  // returns failure if stream cannot be made ready and stream
-  // should be canceled
-  nsresult SetFullyOpen();
-
-  bool HasRegisteredID() { return mStreamID != 0; }
-
-  nsAHttpTransaction *Transaction() { return mTransaction; }
-  virtual nsIRequestContext *RequestContext()
-  {
-    return mTransaction ? mTransaction->RequestContext() : nullptr;
-  }
-
-  void Close(nsresult reason);
-  void SetResponseIsComplete();
-
-  void SetRecvdFin(bool aStatus) { mRecvdFin = aStatus ? 1 : 0; }
-  bool RecvdFin() { return mRecvdFin; }
-
-  void SetRecvdData(bool aStatus) { mReceivedData = aStatus ? 1 : 0; }
-  bool RecvdData() { return mReceivedData; }
-
-  void SetQueued(bool aStatus) { mQueued = aStatus ? 1 : 0; }
-  bool Queued() { return mQueued; }
-
-  void SetCountAsActive(bool aStatus) { mCountAsActive = aStatus ? 1 : 0; }
-  bool CountAsActive() { return mCountAsActive; }
-
-  void UpdateTransportSendEvents(uint32_t count);
-  void UpdateTransportReadEvents(uint32_t count);
-
-  // The zlib header compression dictionary defined by SPDY.
-  static const unsigned char kDictionary[1423];
-
-  nsresult Uncompress(z_stream *, char *, uint32_t);
-  nsresult ConvertHeaders(nsACString &);
-
-  void UpdateRemoteWindow(int32_t delta);
-  int64_t RemoteWindow() { return mRemoteWindow; }
-
-  void DecrementLocalWindow(uint32_t delta) {
-    mLocalWindow -= delta;
-    mLocalUnacked += delta;
-  }
-
-  void IncrementLocalWindow(uint32_t delta) {
-    mLocalWindow += delta;
-    mLocalUnacked -= delta;
-  }
-
-  uint64_t LocalUnAcked() { return mLocalUnacked; }
-  int64_t  LocalWindow()  { return mLocalWindow; }
-
-  bool     BlockedOnRwin() { return mBlockedOnRwin; }
-  bool     ChannelPipeFull();
-
-  // A pull stream has an implicit sink, a pushed stream has a sink
-  // once it is matched to a pull stream.
-  virtual bool HasSink() { return true; }
-
-  virtual ~SpdyStream31();
-
-protected:
-  nsresult FindHeader(nsCString, nsDependentCSubstring &);
-
-  static void CreatePushHashKey(const nsCString &scheme,
-                                const nsCString &hostHeader,
-                                uint64_t serial,
-                                const nsCSubstring &pathInfo,
-                                nsCString &outOrigin,
-                                nsCString &outKey);
-
-  enum stateType {
-    GENERATING_SYN_STREAM,
-    GENERATING_REQUEST_BODY,
-    SENDING_REQUEST_BODY,
-    SENDING_FIN_STREAM,
-    UPSTREAM_COMPLETE
-  };
-
-  uint32_t mStreamID;
-
-  // The session that this stream is a subset of
-  SpdySession31 *mSession;
-
-  nsCString     mOrigin;
-
-  // Each stream goes from syn_stream to upstream_complete, perhaps
-  // looping on multiple instances of generating_request_body and
-  // sending_request_body for each SPDY chunk in the upload.
-  enum stateType mUpstreamState;
-
-  // Flag is set when all http request headers have been read
-  uint32_t                     mRequestHeadersDone   : 1;
-
-  // Flag is set when stream ID is stable
-  uint32_t                     mSynFrameGenerated    : 1;
-
-  // Flag is set when a FIN has been placed on a data or syn packet
-  // (i.e after the client has closed)
-  uint32_t                     mSentFinOnData        : 1;
-
-  // Flag is set when stream is queued inside the session due to
-  // concurrency limits being exceeded
-  uint32_t                     mQueued               : 1;
-
-  void     ChangeState(enum stateType);
-
-private:
-  friend class nsAutoPtr<SpdyStream31>;
-
-  nsresult ParseHttpRequestHeaders(const char *, uint32_t, uint32_t *);
-  nsresult GenerateSynFrame();
-
-  void     AdjustInitialWindow();
-  nsresult TransmitFrame(const char *, uint32_t *, bool forceCommitment);
-  void     GenerateDataFrameHeader(uint32_t, bool);
-
-  void     CompressToFrame(const nsACString &);
-  void     CompressToFrame(const nsACString *);
-  void     CompressToFrame(const char *, uint32_t);
-  void     CompressToFrame(uint32_t);
-  void     CompressFlushFrame();
-  void     ExecuteCompress(uint32_t);
-
-  // The underlying HTTP transaction. This pointer is used as the key
-  // in the SpdySession31 mStreamTransactionHash so it is important to
-  // keep a reference to it as long as this stream is a member of that hash.
-  // (i.e. don't change it or release it after it is set in the ctor).
-  RefPtr<nsAHttpTransaction> mTransaction;
-
-  // The underlying socket transport object is needed to propogate some events
-  nsISocketTransport         *mSocketTransport;
-
-  // These are temporary state variables to hold the argument to
-  // Read/WriteSegments so it can be accessed by On(read/write)segment
-  // further up the stack.
-  nsAHttpSegmentReader        *mSegmentReader;
-  nsAHttpSegmentWriter        *mSegmentWriter;
-
-  // The quanta upstream data frames are chopped into
-  uint32_t                    mChunkSize;
-
-  // Flag is set when the HTTP processor has more data to send
-  // but has blocked in doing so.
-  uint32_t                     mRequestBlockedOnRead : 1;
-
-  // Flag is set after the response frame bearing the fin bit has
-  // been processed. (i.e. after the server has closed).
-  uint32_t                     mRecvdFin             : 1;
-
-  // Flag is set after syn reply received
-  uint32_t                     mFullyOpen            : 1;
-
-  // Flag is set after the WAITING_FOR Transport event has been generated
-  uint32_t                     mSentWaitingFor       : 1;
-
-  // Flag is set after 1st DATA frame has been passed to stream, after
-  // which additional HEADERS data is invalid
-  uint32_t                     mReceivedData         : 1;
-
-  // Flag is set after TCP send autotuning has been disabled
-  uint32_t                     mSetTCPSocketBuffer   : 1;
-
-  // Flag is set when stream is counted towards MAX_CONCURRENT streams in session
-  uint32_t                     mCountAsActive        : 1;
-
-  // The InlineFrame and associated data is used for composing control
-  // frames and data frame headers.
-  UniquePtr<uint8_t[]>         mTxInlineFrame;
-  uint32_t                     mTxInlineFrameSize;
-  uint32_t                     mTxInlineFrameUsed;
-
-  // mTxStreamFrameSize tracks the progress of
-  // transmitting a request body data frame. The data frame itself
-  // is never copied into the spdy layer.
-  uint32_t                     mTxStreamFrameSize;
-
-  // Compression context and buffer for request header compression.
-  // This is a copy of SpdySession31::mUpstreamZlib because it needs
-  //  to remain the same in all streams of a session.
-  z_stream                     *mZlib;
-  nsCString                    mFlatHttpRequestHeaders;
-
-  // These are used for decompressing downstream spdy response headers
-  uint32_t             mDecompressBufferSize;
-  uint32_t             mDecompressBufferUsed;
-  uint32_t             mDecompressedBytes;
-  UniquePtr<char[]>    mDecompressBuffer;
-
-  // Track the content-length of a request body so that we can
-  // place the fin flag on the last data packet instead of waiting
-  // for a stream closed indication. Relying on stream close results
-  // in an extra 0-length runt packet and seems to have some interop
-  // problems with the google servers. Connect does rely on stream
-  // close by setting this to the max value.
-  int64_t                      mRequestBodyLenRemaining;
-
-  // based on nsISupportsPriority definitions
-  int32_t                      mPriority;
-
-  // mLocalWindow, mRemoteWindow, and mLocalUnacked are for flow control.
-  // *window are signed because the race conditions in asynchronous SETTINGS
-  // messages can force them temporarily negative.
-
-  // LocalWindow is how much data the server will send without getting a
-  //   window update
-  int64_t                      mLocalWindow;
-
-  // RemoteWindow is how much data the client is allowed to send without
-  //   getting a window update
-  int64_t                      mRemoteWindow;
-
-  // LocalUnacked is the number of bytes received by the client but not
-  //   yet reflected in a window update. Sending that update will increment
-  //   LocalWindow
-  uint64_t                     mLocalUnacked;
-
-  // True when sending is suspended becuase the remote flow control window is
-  //   <= 0
-  bool                         mBlockedOnRwin;
-
-  // For Progress Events
-  uint64_t                     mTotalSent;
-  uint64_t                     mTotalRead;
-
-  // For SpdyPush
-  SpdyPushedStream31 *mPushSource;
-
-/// connect tunnels
-public:
-  bool IsTunnel() { return mIsTunnel; }
-private:
-  void ClearTransactionsBlockedOnTunnel();
-  void MapStreamToPlainText();
-  void MapStreamToHttpConnection();
-
-  bool mIsTunnel;
-  bool mPlainTextTunnel;
-};
-
-} // namespace net
-} // namespace mozilla
-
-#endif // mozilla_net_SpdyStream31_h
deleted file mode 100644
--- a/netwerk/protocol/http/SpdyZlibReporter.cpp
+++ /dev/null
@@ -1,39 +0,0 @@
-/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
-/* vim: set sw=2 ts=8 et tw=80 : */
-/* This Source Code Form is subject to the terms of the Mozilla Public
- * License, v. 2.0. If a copy of the MPL was not distributed with this
- * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
-
-#include "SpdyZlibReporter.h"
-
-namespace mozilla {
-
-NS_IMPL_ISUPPORTS(SpdyZlibReporter, nsIMemoryReporter)
-
-/* static */ Atomic<size_t> SpdyZlibReporter::sAmount;
-
-/* static */ void*
-SpdyZlibReporter::Alloc(void*, uInt items, uInt size)
-{
-  void* p = moz_xmalloc(items * size);
-  sAmount += MallocSizeOfOnAlloc(p);
-  return p;
-}
-
-/* static */ void
-SpdyZlibReporter::Free(void*, void* p)
-{
-  sAmount -= MallocSizeOfOnFree(p);
-  free(p);
-}
-
-NS_IMETHODIMP
-SpdyZlibReporter::CollectReports(nsIHandleReportCallback* aHandleReport,
-                                 nsISupports* aData, bool aAnonymize)
-{
-  return MOZ_COLLECT_REPORT(
-    "explicit/network/spdy-zlib-buffers", KIND_HEAP, UNITS_BYTES, sAmount,
-    "Memory allocated for SPDY zlib send and receive buffers.");
-}
-
-} // namespace mozilla
deleted file mode 100644
--- a/netwerk/protocol/http/SpdyZlibReporter.h
+++ /dev/null
@@ -1,58 +0,0 @@
-/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
-/* vim: set sw=2 ts=8 et tw=80 : */
-/* This Source Code Form is subject to the terms of the Mozilla Public
- * License, v. 2.0. If a copy of the MPL was not distributed with this
- * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
-
-/* A memory allocator for zlib use in SPDY that reports to about:memory. */
-
-#ifndef mozilla_net_SpdyZlibReporter_h
-#define mozilla_net_SpdyZlibReporter_h
-
-#include "mozilla/Assertions.h"
-#include "mozilla/Atomics.h"
-#include "mozilla/Attributes.h"
-#include "nsIMemoryReporter.h"
-#include "zlib.h"
-
-namespace mozilla {
-
-class SpdyZlibReporter final : public nsIMemoryReporter
-{
-  ~SpdyZlibReporter() {}
-
-public:
-  NS_DECL_ISUPPORTS
-
-  SpdyZlibReporter()
-  {
-#ifdef DEBUG
-    // There must be only one instance of this class, due to |sAmount|
-    // being static.
-    static bool hasRun = false;
-    MOZ_ASSERT(!hasRun);
-    hasRun = true;
-#endif
-    sAmount = 0;
-  }
-
-  static void* Alloc(void*, uInt items, uInt size);
-  static void Free(void*, void* p);
-
-private:
-  // |sAmount| can be (implicitly) accessed by multiple threads, so it
-  // must be thread-safe.
-  static Atomic<size_t> sAmount;
-
-  MOZ_DEFINE_MALLOC_SIZE_OF(MallocSizeOf)
-  MOZ_DEFINE_MALLOC_SIZE_OF_ON_ALLOC(MallocSizeOfOnAlloc)
-  MOZ_DEFINE_MALLOC_SIZE_OF_ON_FREE(MallocSizeOfOnFree)
-
-  NS_IMETHODIMP
-  CollectReports(nsIHandleReportCallback* aHandleReport, nsISupports* aData,
-                 bool aAnonymize) override;
-};
-
-} // namespace mozilla
-
-#endif // mozilla_net_SpdyZlibReporter_h
--- a/netwerk/protocol/http/moz.build
+++ b/netwerk/protocol/http/moz.build
@@ -80,20 +80,16 @@ UNIFIED_SOURCES += [
     'nsHttpPipeline.cpp',
     'nsHttpRequestHead.cpp',
     'nsHttpResponseHead.cpp',
     'nsHttpTransaction.cpp',
     'NullHttpChannel.cpp',
     'NullHttpTransaction.cpp',
     'PackagedAppService.cpp',
     'PackagedAppVerifier.cpp',
-    'SpdyPush31.cpp',
-    'SpdySession31.cpp',
-    'SpdyStream31.cpp',
-    'SpdyZlibReporter.cpp',
     'TunnelUtils.cpp',
 ]
 
 # These files cannot be built in unified mode because of OS X headers.
 SOURCES += [
     'nsHttpHandler.cpp',
 ]
 
--- a/netwerk/protocol/http/nsHttp.cpp
+++ b/netwerk/protocol/http/nsHttp.cpp
@@ -226,18 +226,16 @@ nsHttp::IsValidToken(const char *start, 
 
     return true;
 }
 
 const char*
 nsHttp::GetProtocolVersion(uint32_t pv)
 {
     switch (pv) {
-    case SPDY_VERSION_31:
-        return "spdy/3.1";
     case HTTP_VERSION_2:
     case NS_HTTP_VERSION_2_0:
         return "h2";
     case NS_HTTP_VERSION_1_0:
         return "http/1.0";
     case NS_HTTP_VERSION_1_1:
         return "http/1.1";
     default:
--- a/netwerk/protocol/http/nsHttp.h
+++ b/netwerk/protocol/http/nsHttp.h
@@ -25,17 +25,17 @@
 namespace mozilla {
 
 class Mutex;
 
 namespace net {
     enum {
         // SPDY_VERSION_2 = 2, REMOVED
         // SPDY_VERSION_3 = 3, REMOVED
-        SPDY_VERSION_31 = 4,
+        // SPDY_VERSION_31 = 4, REMOVED
         HTTP_VERSION_2 = 5
 
         // leave room for official versions. telem goes to 48
         // 24 was a internal spdy/3.1
         // 25 was spdy/4a2
         // 26 was http/2-draft08 and http/2-draft07 (they were the same)
         // 27 was http/2-draft09, h2-10, and h2-11
         // 28 was http/2-draft12
--- a/netwerk/protocol/http/nsHttpHandler.cpp
+++ b/netwerk/protocol/http/nsHttpHandler.cpp
@@ -39,17 +39,16 @@
 #include "Tickler.h"
 #include "nsIXULAppInfo.h"
 #include "nsICookieService.h"
 #include "nsIObserverService.h"
 #include "nsISiteSecurityService.h"
 #include "nsIStreamConverterService.h"
 #include "nsITimer.h"
 #include "nsCRT.h"
-#include "SpdyZlibReporter.h"
 #include "nsIMemoryReporter.h"
 #include "nsIParentalControlsService.h"
 #include "nsPIDOMWindow.h"
 #include "nsINetworkLinkService.h"
 #include "nsHttpChannelAuthProvider.h"
 #include "nsServiceManagerUtils.h"
 #include "nsComponentManagerUtils.h"
 #include "nsSocketTransportService2.h"
@@ -205,17 +204,16 @@ nsHttpHandler::nsHttpHandler()
     , mDoNotTrackEnabled(false)
     , mSafeHintEnabled(false)
     , mParentalControlEnabled(false)
     , mHandlerActive(false)
     , mTelemetryEnabled(false)
     , mAllowExperiments(true)
     , mDebugObservations(false)
     , mEnableSpdy(false)
-    , mSpdyV31(true)
     , mHttp2Enabled(true)
     , mUseH2Deps(true)
     , mEnforceHttp2TlsProfile(true)
     , mCoalesceSpdy(true)
     , mSpdyPersistentSettings(false)
     , mAllowPush(true)
     , mEnableAltSvc(false)
     , mEnableAltSvcOE(false)
@@ -238,18 +236,16 @@ nsHttpHandler::nsHttpHandler()
     , mTCPKeepaliveShortLivedIdleTimeS(10)
     , mTCPKeepaliveLongLivedEnabled(false)
     , mTCPKeepaliveLongLivedIdleTimeS(600)
     , mEnforceH1Framing(FRAMECHECK_BARELY)
     , mKeepEmptyResponseHeadersAsEmtpyString(false)
 {
     LOG(("Creating nsHttpHandler [this=%p].\n", this));
 
-    RegisterStrongMemoryReporter(new SpdyZlibReporter());
-
     MOZ_ASSERT(!gHttpHandler, "HTTP handler already created!");
     gHttpHandler = this;
 }
 
 nsHttpHandler::~nsHttpHandler()
 {
     LOG(("Deleting nsHttpHandler [this=%p]\n", this));
 
@@ -1314,22 +1310,16 @@ nsHttpHandler::PrefsChanged(nsIPrefBranc
     }
 
     if (PREF_CHANGED(HTTP_PREF("spdy.enabled"))) {
         rv = prefs->GetBoolPref(HTTP_PREF("spdy.enabled"), &cVar);
         if (NS_SUCCEEDED(rv))
             mEnableSpdy = cVar;
     }
 
-    if (PREF_CHANGED(HTTP_PREF("spdy.enabled.v3-1"))) {
-        rv = prefs->GetBoolPref(HTTP_PREF("spdy.enabled.v3-1"), &cVar);
-        if (NS_SUCCEEDED(rv))
-            mSpdyV31 = cVar;
-    }
-
     if (PREF_CHANGED(HTTP_PREF("spdy.enabled.http2"))) {
         rv = prefs->GetBoolPref(HTTP_PREF("spdy.enabled.http2"), &cVar);
         if (NS_SUCCEEDED(rv))
             mHttp2Enabled = cVar;
     }
 
     if (PREF_CHANGED(HTTP_PREF("spdy.enabled.deps"))) {
         rv = prefs->GetBoolPref(HTTP_PREF("spdy.enabled.deps"), &cVar);
--- a/netwerk/protocol/http/nsHttpHandler.h
+++ b/netwerk/protocol/http/nsHttpHandler.h
@@ -103,17 +103,16 @@ public:
     uint32_t       MaxSocketCount();
     bool           EnforceAssocReq()         { return mEnforceAssocReq; }
 
     bool           IsPersistentHttpsCachingEnabled() { return mEnablePersistentHttpsCaching; }
     bool           IsTelemetryEnabled() { return mTelemetryEnabled; }
     bool           AllowExperiments() { return mTelemetryEnabled && mAllowExperiments; }
 
     bool           IsSpdyEnabled() { return mEnableSpdy; }
-    bool           IsSpdyV31Enabled() { return mSpdyV31; }
     bool           IsHttp2Enabled() { return mHttp2Enabled; }
     bool           EnforceHttp2TlsProfile() { return mEnforceHttp2TlsProfile; }
     bool           CoalesceSpdy() { return mCoalesceSpdy; }
     bool           UseSpdyPersistentSettings() { return mSpdyPersistentSettings; }
     uint32_t       SpdySendingChunkSize() { return mSpdySendingChunkSize; }
     uint32_t       SpdySendBufferSize()      { return mSpdySendBufferSize; }
     uint32_t       SpdyPushAllowance()       { return mSpdyPushAllowance; }
     uint32_t       SpdyPullAllowance()       { return mSpdyPullAllowance; }
@@ -508,17 +507,16 @@ private:
 
     // The value of network.allow-experiments
     uint32_t           mAllowExperiments : 1;
 
     // The value of 'hidden' network.http.debug-observations : 1;
     uint32_t           mDebugObservations : 1;
 
     uint32_t           mEnableSpdy : 1;
-    uint32_t           mSpdyV31 : 1;
     uint32_t           mHttp2Enabled : 1;
     uint32_t           mUseH2Deps : 1;
     uint32_t           mEnforceHttp2TlsProfile : 1;
     uint32_t           mCoalesceSpdy : 1;
     uint32_t           mSpdyPersistentSettings : 1;
     uint32_t           mAllowPush : 1;
     uint32_t           mEnableAltSvc : 1;
     uint32_t           mEnableAltSvcOE : 1;
--- a/netwerk/test/unit/test_http2.js
+++ b/netwerk/test/unit/test_http2.js
@@ -995,30 +995,28 @@ function addCertOverride(host, port, bit
     req.send(null);
   } catch (e) {
     // This will fail since the server is not trusted yet
   }
 }
 
 var prefs;
 var spdypref;
-var spdy3pref;
 var spdypush;
 var http2pref;
 var tlspref;
 var altsvcpref1;
 var altsvcpref2;
 var loadGroup;
 var serverPort;
 var speculativeLimit;
 
 function resetPrefs() {
   prefs.setIntPref("network.http.speculative-parallel-limit", speculativeLimit);
   prefs.setBoolPref("network.http.spdy.enabled", spdypref);
-  prefs.setBoolPref("network.http.spdy.enabled.v3-1", spdy3pref);
   prefs.setBoolPref("network.http.spdy.allow-push", spdypush);
   prefs.setBoolPref("network.http.spdy.enabled.http2", http2pref);
   prefs.setBoolPref("network.http.spdy.enforce-tls-profile", tlspref);
   prefs.setBoolPref("network.http.altsvc.enabled", altsvcpref1);
   prefs.setBoolPref("network.http.altsvc.oe", altsvcpref2);
 }
 
 function run_test() {
@@ -1035,17 +1033,16 @@ function run_test() {
 
   addCertOverride("localhost", serverPort,
                   Ci.nsICertOverrideService.ERROR_UNTRUSTED |
                   Ci.nsICertOverrideService.ERROR_MISMATCH |
                   Ci.nsICertOverrideService.ERROR_TIME);
 
   // Enable all versions of spdy to see that we auto negotiate http/2
   spdypref = prefs.getBoolPref("network.http.spdy.enabled");
-  spdy3pref = prefs.getBoolPref("network.http.spdy.enabled.v3-1");
   spdypush = prefs.getBoolPref("network.http.spdy.allow-push");
   http2pref = prefs.getBoolPref("network.http.spdy.enabled.http2");
   tlspref = prefs.getBoolPref("network.http.spdy.enforce-tls-profile");
   altsvcpref1 = prefs.getBoolPref("network.http.altsvc.enabled");
   altsvcpref2 = prefs.getBoolPref("network.http.altsvc.oe", true);
 
   prefs.setBoolPref("network.http.spdy.enabled", true);
   prefs.setBoolPref("network.http.spdy.enabled.v3-1", true);
deleted file mode 100644
--- a/netwerk/test/unit/test_spdy.js
+++ /dev/null
@@ -1,476 +0,0 @@
-// test spdy/3.1
-
-Cu.import("resource://gre/modules/NetUtil.jsm");
-
-// Generate a small and a large post with known pre-calculated md5 sums
-function generateContent(size) {
-  var content = "";
-  for (var i = 0; i < size; i++) {
-    content += "0";
-  }
-  return content;
-}
-
-var posts = [];
-posts.push(generateContent(10));
-posts.push(generateContent(250000));
-
-// pre-calculated md5sums (in hex) of the above posts
-var md5s = ['f1b708bba17f1ce948dc979f4d7092bc',
-            '2ef8d3b6c8f329318eb1a119b12622b6'];
-
-var bigListenerData = generateContent(128 * 1024);
-var bigListenerMD5 = '8f607cfdd2c87d6a7eedb657dafbd836';
-var hugeListenerData = generateContent(800 * 1024);
-
-function checkIsSpdy(request) {
-  try {
-    if (request.getResponseHeader("X-Firefox-Spdy") == "3.1") {
-      if (request.getResponseHeader("X-Connection-Spdy") == "yes") {
-        return true;
-      }
-      return false; // Weird case, but the server disagrees with us
-    }
-  } catch (e) {
-    // Nothing to do here
-  }
-  return false;
-}
-
-var SpdyCheckListener = function() {};
-
-SpdyCheckListener.prototype = {
-  onStartRequestFired: false,
-  onDataAvailableFired: false,
-  isSpdyConnection: false,
-
-  onStartRequest: function testOnStartRequest(request, ctx) {
-    this.onStartRequestFired = true;
-    if (!Components.isSuccessCode(request.status))
-      do_throw("Channel should have a success code! (" + request.status + ")");
-
-    do_check_true(request instanceof Components.interfaces.nsIHttpChannel);
-    do_check_eq(request.responseStatus, 200);
-    do_check_eq(request.requestSucceeded, true);
-  },
-
-  onDataAvailable: function testOnDataAvailable(request, ctx, stream, off, cnt) {
-    this.onDataAvailableFired = true;
-    this.isSpdyConnection = checkIsSpdy(request);
-
-    read_stream(stream, cnt);
-  },
-
-  onStopRequest: function testOnStopRequest(request, ctx, status) {
-    do_check_true(this.onStartRequestFired);
-    do_check_true(Components.isSuccessCode(status));
-    do_check_true(this.isSpdyConnection);
-    do_check_true(this.onDataAvailableFired);
-
-    run_next_test();
-    do_test_finished();
-  }
-};
-
-/*
- * Support for testing valid multiplexing of streams
- */
-
-var multiplexContent = generateContent(30*1024);
-var completed_channels = [];
-function register_completed_channel(listener) {
-  completed_channels.push(listener);
-  if (completed_channels.length == 2) {
-    do_check_neq(completed_channels[0].streamID, completed_channels[1].streamID);
-    run_next_test();
-    do_test_finished();
-  }
-}
-
-/* Listener class to control the testing of multiplexing */
-var SpdyMultiplexListener = function() {};
-
-SpdyMultiplexListener.prototype = new SpdyCheckListener();
-
-SpdyMultiplexListener.prototype.streamID = 0;
-SpdyMultiplexListener.prototype.buffer = "";
-
-SpdyMultiplexListener.prototype.onDataAvailable = function(request, ctx, stream, off, cnt) {
-  this.onDataAvailableFired = true;
-  this.isSpdyConnection = checkIsSpdy(request);
-  this.streamID = parseInt(request.getResponseHeader("X-Spdy-StreamID"));
-  var data = read_stream(stream, cnt);
-  this.buffer = this.buffer.concat(data);
-};
-
-SpdyMultiplexListener.prototype.onStopRequest = function(request, ctx, status) {
-  do_check_true(this.onStartRequestFired);
-  do_check_true(this.onDataAvailableFired);
-  do_check_true(this.isSpdyConnection);
-  do_check_true(this.buffer == multiplexContent);
-  
-  // This is what does most of the hard work for us
-  register_completed_channel(this);
-};
-
-// Does the appropriate checks for header gatewaying
-var SpdyHeaderListener = function(value) {
-  this.value = value
-};
-
-SpdyHeaderListener.prototype = new SpdyCheckListener();
-SpdyHeaderListener.prototype.value = "";
-
-SpdyHeaderListener.prototype.onDataAvailable = function(request, ctx, stream, off, cnt) {
-  this.onDataAvailableFired = true;
-  this.isSpdyConnection = checkIsSpdy(request);
-  do_check_eq(request.getResponseHeader("X-Received-Test-Header"), this.value);
-  read_stream(stream, cnt);
-};
-
-var SpdyPushListener = function() {};
-
-SpdyPushListener.prototype = new SpdyCheckListener();
-
-SpdyPushListener.prototype.onDataAvailable = function(request, ctx, stream, off, cnt) {
-  this.onDataAvailableFired = true;
-  this.isSpdyConnection = checkIsSpdy(request);
-  if (request.originalURI.spec == "https://localhost:" + serverPort + "/push.js" ||
-      request.originalURI.spec == "https://localhost:" + serverPort + "/push2.js") {
-    do_check_eq(request.getResponseHeader("pushed"), "yes");
-  }
-  read_stream(stream, cnt);
-};
-
-// Does the appropriate checks for a large GET response
-var SpdyBigListener = function() {};
-
-SpdyBigListener.prototype = new SpdyCheckListener();
-SpdyBigListener.prototype.buffer = "";
-
-SpdyBigListener.prototype.onDataAvailable = function(request, ctx, stream, off, cnt) {
-  this.onDataAvailableFired = true;
-  this.isSpdyConnection = checkIsSpdy(request);
-  this.buffer = this.buffer.concat(read_stream(stream, cnt));
-};
-
-SpdyBigListener.prototype.onStopRequest = function(request, ctx, status) {
-  do_check_true(this.onStartRequestFired);
-  do_check_true(this.onDataAvailableFired);
-  do_check_true(this.isSpdyConnection);
-
-  // Don't want to flood output, so don't use do_check_eq
-  if (request.originalURI.spec == "https://localhost:" + serverPort + "/big") {
-    // We know the server should send us the same data as our big post will be,
-    // so the md5 should be the same
-    do_check_eq(bigListenerMD5, request.getResponseHeader("X-Expected-MD5"));
-    do_check_true(this.buffer == bigListenerData);
-  } else {
-    do_check_true(this.buffer == hugeListenerData);
-  }
-
-  run_next_test();
-  do_test_finished();
-};
-
-// Does the appropriate checks for POSTs
-var SpdyPostListener = function(expected_md5) {
-  this.expected_md5 = expected_md5;
-};
-
-SpdyPostListener.prototype = new SpdyCheckListener();
-SpdyPostListener.prototype.expected_md5 = "";
-
-SpdyPostListener.prototype.onDataAvailable = function(request, ctx, stream, off, cnt) {
-  this.onDataAvailableFired = true;
-  this.isSpdyConnection = checkIsSpdy(request);
-  read_stream(stream, cnt);
-  do_check_eq(this.expected_md5, request.getResponseHeader("X-Calculated-MD5"));
-};
-
-function makeChan(url) {
-  return NetUtil.newChannel({uri: url, loadUsingSystemPrincipal: true})
-                .QueryInterface(Ci.nsIHttpChannel);
-}
-
-// Make sure we make a spdy connection and both us and the server mark it as such
-function test_spdy_basic() {
-  var chan = makeChan("https://localhost:" + serverPort + "/");
-  var listener = new SpdyCheckListener();
-  chan.asyncOpen2(listener);
-}
-
-// Support for making sure XHR works over SPDY
-function checkXhr(xhr) {
-  if (xhr.readyState != 4) {
-    return;
-  }
-
-  do_check_eq(xhr.status, 200);
-  do_check_eq(checkIsSpdy(xhr), true);
-  run_next_test();
-  do_test_finished();
-}
-
-// Fires off an XHR request over SPDY
-function test_spdy_xhr() {
-  var req = Cc["@mozilla.org/xmlextras/xmlhttprequest;1"]
-            .createInstance(Ci.nsIXMLHttpRequest);
-  req.open("GET", "https://localhost:" + serverPort + "/", true);
-  req.addEventListener("readystatechange", function (evt) { checkXhr(req); },
-                       false);
-  req.send(null);
-}
-
-var concurrent_channels = [];
-
-var SpdyConcurrentListener = function() {};
-
-SpdyConcurrentListener.prototype = new SpdyCheckListener();
-SpdyConcurrentListener.prototype.count = 0;
-SpdyConcurrentListener.prototype.target = 0;
-
-SpdyConcurrentListener.prototype.onStopRequest = function(request, ctx, status) {
-  this.count++;
-  do_check_true(this.isSpdyConnection);
-  if (this.count == this.target) {
-    run_next_test();
-    do_test_finished();
-  }
-};
-
-function test_spdy_concurrent() {
-  var concurrent_listener = new SpdyConcurrentListener();
-  concurrent_listener.target = 201;
-  for (var i = 0; i < concurrent_listener.target; i++) {
-    concurrent_channels[i] = makeChan("https://localhost:" + serverPort + "/750ms");
-    concurrent_channels[i].loadFlags = Ci.nsIRequest.LOAD_BYPASS_CACHE;
-    concurrent_channels[i].asyncOpen2(concurrent_listener);
-  }
-}
-
-// Test to make sure we get multiplexing right
-function test_spdy_multiplex() {
-  var chan1 = makeChan("https://localhost:" + serverPort + "/multiplex1");
-  var chan2 = makeChan("https://localhost:" + serverPort + "/multiplex2");
-  var listener1 = new SpdyMultiplexListener();
-  var listener2 = new SpdyMultiplexListener();
-  chan1.asyncOpen2(listener1);
-  chan2.asyncOpen2(listener2);
-}
-
-// Test to make sure we gateway non-standard headers properly
-function test_spdy_header() {
-  var chan = makeChan("https://localhost:" + serverPort + "/header");
-  var hvalue = "Headers are fun";
-  var listener = new SpdyHeaderListener(hvalue);
-  chan.setRequestHeader("X-Test-Header", hvalue, false);
-  chan.asyncOpen2(listener);
-}
-
-function test_spdy_push1() {
-  var chan = makeChan("https://localhost:" + serverPort + "/push");
-  chan.loadGroup = loadGroup;
-  var listener = new SpdyPushListener();
-  chan.asyncOpen2(listener);
-}
-
-function test_spdy_push2() {
-  var chan = makeChan("https://localhost:" + serverPort + "/push.js");
-  chan.loadGroup = loadGroup;
-  var listener = new SpdyPushListener();
-  chan.asyncOpen2(listener);
-}
-
-function test_spdy_push3() {
-  var chan = makeChan("https://localhost:" + serverPort + "/push2");
-  chan.loadGroup = loadGroup;
-  var listener = new SpdyPushListener();
-  chan.asyncOpen2(listener);
-}
-
-function test_spdy_push4() {
-  var chan = makeChan("https://localhost:" + serverPort + "/push2.js");
-  chan.loadGroup = loadGroup;
-  var listener = new SpdyPushListener();
-  chan.asyncOpen2(listener);
-}
-
-// Make sure we handle GETs that cover more than 2 frames properly
-function test_spdy_big() {
-  var chan = makeChan("https://localhost:" + serverPort + "/big");
-  var listener = new SpdyBigListener();
-  chan.asyncOpen2(listener);
-}
-
-// Make sure we handle big GETs with suspend/resume
-function test_spdy_big_and_slow() {
-  var chan = makeChan("https://localhost:" + serverPort + "/huge");
-  var listener = new SpdyBigListener();
-  chan.asyncOpen2(listener);
-  chan.suspend();
-  do_timeout(750, chan.resume);
-}
-
-// Support for doing a POST
-function do_post(content, chan, listener) {
-  var stream = Cc["@mozilla.org/io/string-input-stream;1"]
-               .createInstance(Ci.nsIStringInputStream);
-  stream.data = content;
-
-  var uchan = chan.QueryInterface(Ci.nsIUploadChannel);
-  uchan.setUploadStream(stream, "text/plain", stream.available());
-
-  chan.requestMethod = "POST";
-
-  chan.asyncOpen2(listener);
-}
-
-// Make sure we can do a simple POST
-function test_spdy_post() {
-  var chan = makeChan("https://localhost:" + serverPort + "/post");
-  var listener = new SpdyPostListener(md5s[0]);
-  do_post(posts[0], chan, listener);
-}
-
-// Make sure we can do a POST that covers more than 2 frames
-function test_spdy_post_big() {
-  var chan = makeChan("https://localhost:" + serverPort + "/post");
-  var listener = new SpdyPostListener(md5s[1]);
-  do_post(posts[1], chan, listener);
-}
-
-function test_complete() {
-  resetPrefs();
-  do_test_finished();
-  do_timeout(0,run_next_test);
-}
-
-// hack - the header test resets the multiplex object on the server,
-// so make sure header is always run before the multiplex test.
-//
-// make sure post_big runs first to test race condition in restarting
-// a stalled stream when a SETTINGS frame arrives
-var tests = [ test_spdy_post_big
-            , test_spdy_basic
-            , test_spdy_concurrent
-            , test_spdy_push1
-            , test_spdy_push2
-            , test_spdy_push3
-            , test_spdy_push4
-            , test_spdy_xhr
-            , test_spdy_header
-            , test_spdy_multiplex
-            , test_spdy_big
-            , test_spdy_big_and_slow
-            , test_spdy_post
-            // cleanup
-            , test_complete
-            ];
-var current_test = 0;
-
-function run_next_test() {
-  if (current_test < tests.length) {
-    tests[current_test]();
-    current_test++;
-    do_test_pending();
-  }
-}
-
-// Support for making sure we can talk to the invalid cert the server presents
-var CertOverrideListener = function(host, port, bits) {
-  this.host = host;
-  if (port) {
-    this.port = port;
-  }
-  this.bits = bits;
-};
-
-CertOverrideListener.prototype = {
-  host: null,
-  port: -1,
-  bits: null,
-
-  getInterface: function(aIID) {
-    return this.QueryInterface(aIID);
-  },
-
-  QueryInterface: function(aIID) {
-    if (aIID.equals(Ci.nsIBadCertListener2) ||
-        aIID.equals(Ci.nsIInterfaceRequestor) ||
-        aIID.equals(Ci.nsISupports))
-      return this;
-    throw Components.results.NS_ERROR_NO_INTERFACE;
-  },
-
-  notifyCertProblem: function(socketInfo, sslStatus, targetHost) {
-    var cert = sslStatus.QueryInterface(Ci.nsISSLStatus).serverCert;
-    var cos = Cc["@mozilla.org/security/certoverride;1"].
-              getService(Ci.nsICertOverrideService);
-    cos.rememberValidityOverride(this.host, this.port, cert, this.bits, false);
-    dump("Certificate Override in place\n");
-    return true;
-  },
-};
-
-function addCertOverride(host, port, bits) {
-  var req = Cc["@mozilla.org/xmlextras/xmlhttprequest;1"]
-            .createInstance(Ci.nsIXMLHttpRequest);
-  try {
-    var url;
-    if (port) {
-      url = "https://" + host + ":" + port + "/";
-    } else {
-      url = "https://" + host + "/";
-    }
-    req.open("GET", url, false);
-    req.channel.notificationCallbacks = new CertOverrideListener(host, port, bits);
-    req.send(null);
-  } catch (e) {
-    // This will fail since the server is not trusted yet
-  }
-}
-
-var prefs;
-var spdypref;
-var spdy3pref;
-var spdypush;
-var loadGroup;
-var serverPort;
-
-function resetPrefs() {
-  prefs.setBoolPref("network.http.spdy.enabled", spdypref);
-  prefs.setBoolPref("network.http.spdy.enabled.v3-1", spdy3pref);
-  prefs.setBoolPref("network.http.spdy.allow-push", spdypush);
-}
-
-function run_test() {
-  var env = Cc["@mozilla.org/process/environment;1"].getService(Ci.nsIEnvironment);
-  serverPort = env.get("MOZSPDY_PORT");
-  do_check_neq(serverPort, null);
-  dump("using port " + serverPort + "\n");
-
-  // Set to allow the cert presented by our SPDY server
-  do_get_profile();
-  prefs = Cc["@mozilla.org/preferences-service;1"].getService(Ci.nsIPrefBranch);
-  var oldParallel = prefs.getIntPref("network.http.speculative-parallel-limit");
-  prefs.setIntPref("network.http.speculative-parallel-limit", 0);
-
-  addCertOverride("localhost", serverPort,
-                  Ci.nsICertOverrideService.ERROR_UNTRUSTED |
-                  Ci.nsICertOverrideService.ERROR_MISMATCH |
-                  Ci.nsICertOverrideService.ERROR_TIME);
-  prefs.setIntPref("network.http.speculative-parallel-limit", oldParallel);
-
-  // Enable all versions of spdy to see that we auto negotiate spdy/3.1
-  spdypref = prefs.getBoolPref("network.http.spdy.enabled");
-  spdy3pref = prefs.getBoolPref("network.http.spdy.enabled.v3-1");
-  spdypush = prefs.getBoolPref("network.http.spdy.allow-push");
-  prefs.setBoolPref("network.http.spdy.enabled", true);
-  prefs.setBoolPref("network.http.spdy.enabled.v3-1", true);
-  prefs.setBoolPref("network.http.spdy.allow-push", true);
-
-  loadGroup = Cc["@mozilla.org/network/load-group;1"].createInstance(Ci.nsILoadGroup);
-
-  run_next_test();
-}
--- a/netwerk/test/unit/xpcshell.ini
+++ b/netwerk/test/unit/xpcshell.ini
@@ -278,20 +278,17 @@ fail-if = os == "android"
 [test_resumable_channel.js]
 [test_resumable_truncate.js]
 [test_safeoutputstream.js]
 [test_simple.js]
 [test_sockettransportsvc_available.js]
 [test_socks.js]
 # Bug 675039: test fails consistently on Android
 fail-if = os == "android"
-# spdy and http2 unit tests require us to have node available to run the spdy and http2 server
-[test_spdy.js]
-skip-if = !hasNode
-run-sequentially = node server exceptions dont replay well
+# http2 unit tests require us to have node available to run the spdy and http2 server
 [test_http2.js]
 skip-if = !hasNode
 run-sequentially = node server exceptions dont replay well
 [test_altsvc.js]
 skip-if = !hasNode
 run-sequentially = node server exceptions dont replay well
 [test_speculative_connect.js]
 [test_standardurl.js]
deleted file mode 100644
--- a/testing/xpcshell/moz-spdy/README.txt
+++ /dev/null
@@ -1,14 +0,0 @@
-Test server for SPDY unit tests. To run it, you need node >= 0.7.0 (not provided)
-and node-spdy (provided). Just run
-
-node /path/to/moz-spdy.js
-
-And you will get a SPDY server listening on port 4443, then you can run the
-xpcshell unit tests in netwerk/test/unit/test_spdy.js
-
-*** A NOTE ON TLS CERTIFICATES ***
-
-The certificates used for this test (*.pem in this directory) are the ones
-provided as examples by node-spdy, and are copied directly from keys/ under
-its top-level source directory (slightly renamed to match the option names
-in the options dictionary passed to spdy.createServer).
deleted file mode 100644
--- a/testing/xpcshell/moz-spdy/moz-spdy.js
+++ /dev/null
@@ -1,197 +0,0 @@
-/* This Source Code Form is subject to the terms of the Mozilla Public
- * License, v. 2.0. If a copy of the MPL was not distributed with this
- * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
-
-var spdy = require('../node-spdy/lib/spdy.js');
-var fs = require('fs');
-var url = require('url');
-var crypto = require('crypto');
-
-function getHttpContent(path) {
-  var content = '<!doctype html>' +
-                '<html>' +
-                '<head><title>HOORAY!</title></head>' +
-                '<body>You Win! (by requesting' + path + ')</body>' +
-                '</html>';
-  return content;
-}
-
-function getHugeContent(size) {
-  var content = '';
-
-  for (var i = 0; i < size; i++) {
-    content += '0';
-  }
-
-  return content;
-}
-
-/* This takes care of responding to the multiplexed request for us */
-var Multiplex = function() {};
-
-Multiplex.prototype = {
-  mp1res: null,
-  mp2res: null,
-  buf: null,
-  mp1start: 0,
-  mp2start: 0,
-
-  checkReady: function() {
-    if (this.mp1res != null && this.mp2res != null) {
-      this.buf = getHugeContent(30*1024);
-      this.mp1start = 0;
-      this.mp2start = 0;
-      this.send(this.mp1res, 0);
-      setTimeout(function() { this.send(this.mp2res, 0); }.bind(this), 5);
-    }
-  },
-
-  send: function(res, start) {
-    var end = start + 1024;
-    if (end > this.buf.length)
-      end = this.buf.length;
-    var content = this.buf.substring(start, end);
-    if (end < this.buf.length) {
-      res.write(content);
-      setTimeout(function() { this.send(res, end); }.bind(this), 10);
-    } else {
-      res.end(content);
-    }
-  },
-};
-
-var m = new Multiplex();
-
-var post_hash = null;
-function receivePostData(chunk) {
-  post_hash.update(chunk.toString());
-}
-
-function finishPost(res, content) {
-  var md5 = post_hash.digest('hex');
-  res.setHeader('X-Calculated-MD5', md5);
-  res.writeHead(200);
-  res.end(content);
-}
-
-var runlater = function() {};
-runlater.prototype = {
-  req : null,
-  resp : null,
-
-  onTimeout : function onTimeout() {
-    this.resp.writeHead(200);
-    this.resp.end("It's all good spdy 750ms.");
-  }
-};
-
-function executeRunLater(arg) {
-  arg.onTimeout();
-}
-
-function handleRequest(req, res) {
-  var u = url.parse(req.url);
-  var content = getHttpContent(u.pathname);
-
-  if (req.streamID) {
-    res.setHeader('X-Connection-Spdy', 'yes');
-    res.setHeader('X-Spdy-StreamId', '' + req.streamID);
-  } else {
-    res.setHeader('X-Connection-Spdy', 'no');
-  }
-
-  if (u.pathname === '/750ms') {
-    var rl = new runlater();
-    rl.req = req;
-    rl.resp = res;
-    setTimeout(executeRunLater, 750, rl);
-    return;
-  }
-
-  if (u.pathname == '/exit') {
-    res.setHeader('Content-Type', 'text/plain');
-    res.writeHead(200);
-    res.end('ok');
-    process.exit();
-  } else if (u.pathname == '/multiplex1' && req.streamID) {
-    res.setHeader('Content-Type', 'text/plain');
-    res.writeHead(200);
-    m.mp1res = res;
-    m.checkReady();
-    return;
-  } else if (u.pathname == '/multiplex2' && req.streamID) {
-    res.setHeader('Content-Type', 'text/plain');
-    res.writeHead(200);
-    m.mp2res = res;
-    m.checkReady();
-    return;
-  } else if (u.pathname == "/header") {
-    m = new Multiplex();
-    var val = req.headers["x-test-header"];
-    if (val) {
-      res.setHeader("X-Received-Test-Header", val);
-    }
-  } else if (u.pathname == "/push") {
-    var stream = res.push('/push.js',
-     { 'content-type': 'application/javascript',
-       'pushed' : 'yes',
-       'content-length' : 11,
-       'X-Connection-Spdy': 'yes'});
-      stream.on('error', function(){});
-      stream.end('// comments');
-      content = '<head> <script src="push.js"/></head>body text';
-  } else if (u.pathname == "/push2") {
-      var stream = res.push('/push2.js',
-       { 'content-type': 'application/javascript',
-	 'pushed' : 'yes',
-	 // no content-length
-	 'X-Connection-Spdy': 'yes'});
-      stream.on('error', function(){});
-      stream.end('// comments');
-      content = '<head> <script src="push2.js"/></head>body text';
-  } else if (u.pathname == "/big") {
-    content = getHugeContent(128 * 1024);
-    var hash = crypto.createHash('md5');
-    hash.update(content);
-    var md5 = hash.digest('hex');
-    res.setHeader("X-Expected-MD5", md5);
-  } else if (u.pathname == "/huge") {
-    content = getHugeContent(800 * 1024);
-  } else if (u.pathname == "/post") {
-    if (req.method != "POST") {
-      res.writeHead(405);
-      res.end('Unexpected method: ' + req.method);
-      return;
-    }
-
-    post_hash = crypto.createHash('md5');
-    req.on('data', receivePostData);
-    req.on('end', function () { finishPost(res, content); });
-
-    return;
-  }
-
-  res.setHeader('Content-Type', 'text/html');
-  res.writeHead(200);
-  res.end(content);
-}
-
-// Set up the SSL certs for our server
-var options = {
-  key: fs.readFileSync(__dirname + '/spdy-key.pem'),
-  cert: fs.readFileSync(__dirname + '/spdy-cert.pem'),
-  ca: fs.readFileSync(__dirname + '/spdy-ca.pem'),
-  windowSize: 16000000,
-};
-
-function listenok() {
-  console.log('SPDY server listening on port ' + webServer.address().port);
-}
-
-var webServer = spdy.createServer(options, handleRequest).listen(0, "0.0.0.0", 200, listenok);
-
-// Set up to exit when the user finishes our stdin
-process.stdin.resume();
-process.stdin.on('end', function () {
-  process.exit();
-});
deleted file mode 100644
--- a/testing/xpcshell/moz-spdy/spdy-ca.pem
+++ /dev/null
@@ -1,11 +0,0 @@
------BEGIN CERTIFICATE REQUEST-----
-MIIBkzCB/QIBADBUMQswCQYDVQQGEwJSVTETMBEGA1UECBMKU29tZS1TdGF0ZTEN
-MAsGA1UEBxMET21zazEhMB8GA1UEChMYSW50ZXJuZXQgV2lkZ2l0cyBQdHkgTHRk
-MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQDVufbmw+S/jrCXvQF9/Gtp2WRF
-3/Gnld/wcOE9J/M01y0RFiyVdPZ9fsOZ93nDVdNWqoaoniLOnlV7ChU4cDy5q+je
-i+mA1ZqyKXnMANZozVPSedXRGwVtlbM5OabVTcPjwrytbcXmQ5np/jJGr1BPWAX+
-A3vk+3j3hjJjIm79rwIDAQABoAAwDQYJKoZIhvcNAQEFBQADgYEAiNWhz6EppIVa
-FfUaB3sLeqfamb9tg9kBHtvqj/FJni0snqms0kPWaTySEPHZF0irIb7VVdq/sVCb
-3gseMVSyoDvPJ4lHC3PXqGQ7kM1mIPhDnR/4HDA3BhlGhTXSDIHgZnvI+HMBdsyC
-hC3dz5odyKqe4nmoofomALkBL9t4H8s=
------END CERTIFICATE REQUEST-----
deleted file mode 100644
--- a/testing/xpcshell/moz-spdy/spdy-cert.pem
+++ /dev/null
@@ -1,14 +0,0 @@
------BEGIN CERTIFICATE-----
-MIICHzCCAYgCCQCPPSUAa8QZojANBgkqhkiG9w0BAQUFADBUMQswCQYDVQQGEwJS
-VTETMBEGA1UECBMKU29tZS1TdGF0ZTENMAsGA1UEBxMET21zazEhMB8GA1UEChMY
-SW50ZXJuZXQgV2lkZ2l0cyBQdHkgTHRkMB4XDTExMDQwOTEwMDY0NVoXDTExMDUw
-OTEwMDY0NVowVDELMAkGA1UEBhMCUlUxEzARBgNVBAgTClNvbWUtU3RhdGUxDTAL
-BgNVBAcTBE9tc2sxITAfBgNVBAoTGEludGVybmV0IFdpZGdpdHMgUHR5IEx0ZDCB
-nzANBgkqhkiG9w0BAQEFAAOBjQAwgYkCgYEA1bn25sPkv46wl70BffxradlkRd/x
-p5Xf8HDhPSfzNNctERYslXT2fX7Dmfd5w1XTVqqGqJ4izp5VewoVOHA8uavo3ovp
-gNWasil5zADWaM1T0nnV0RsFbZWzOTmm1U3D48K8rW3F5kOZ6f4yRq9QT1gF/gN7
-5Pt494YyYyJu/a8CAwEAATANBgkqhkiG9w0BAQUFAAOBgQBuRZisIViI2G/R+w79
-vk21TzC/cJ+O7tKsseDqotXYTH8SuimEH5IWcXNgnWhNzczwN8s2362NixyvCipV
-yd4wzMpPbjIhnWGM0hluWZiK2RxfcqimIBjDParTv6CMUIuwGQ257THKY8hXGg7j
-Uws6Lif3P9UbsuRiYPxMgg98wg==
------END CERTIFICATE-----
deleted file mode 100644
--- a/testing/xpcshell/moz-spdy/spdy-key.pem
+++ /dev/null
@@ -1,15 +0,0 @@
------BEGIN RSA PRIVATE KEY-----
-MIICXAIBAAKBgQDVufbmw+S/jrCXvQF9/Gtp2WRF3/Gnld/wcOE9J/M01y0RFiyV
-dPZ9fsOZ93nDVdNWqoaoniLOnlV7ChU4cDy5q+jei+mA1ZqyKXnMANZozVPSedXR
-GwVtlbM5OabVTcPjwrytbcXmQ5np/jJGr1BPWAX+A3vk+3j3hjJjIm79rwIDAQAB
-AoGAAv2QI9h32epQND9TxwSCKD//dC7W/cZOFNovfKCTeZjNK6EIzKqPTGA6smvR
-C1enFl5adf+IcyWqAoe4lkqTvurIj+2EhtXdQ8DBlVuXKr3xvEFdYxXPautdTCF6
-KbXEyS/s1TZCRFjYftvCrXxc3pK45AQX/wg7z1K+YB5pyIECQQD0OJvLoxLYoXAc
-FZraIOZiDsEbGuSHqoCReFXH75EC3+XGYkH2bQ/nSIZ0h1buuwQ/ylKXOlTPT3Qt
-Xm1OQEBvAkEA4AjWsIO/rRpOm/Q2aCrynWMpoUXTZSbL2yGf8pxp/+8r2br5ier0
-M1LeBb/OPY1+k39NWLXxQoo64xoSFYk2wQJAd2wDCwX4HkR7HNCXw1hZL9QFK6rv
-20NN0VSlpboJD/3KT0MW/FiCcVduoCbaJK0Au+zEjDyy4hj5N4I4Mw6KMwJAXVAx
-I+psTsxzS4/njXG+BgIEl/C+gRYsuMQDnAi8OebDq/et8l0Tg8ETSu++FnM18neG
-ntmBeMacinUUbTXuwQJBAJp/onZdsMzeVulsGrqR1uS+Lpjc5Q1gt5ttt2cxj91D
-rio48C/ZvWuKNE8EYj2ALtghcVKRvgaWfOxt2GPguGg=
------END RSA PRIVATE KEY-----
deleted file mode 100644
--- a/testing/xpcshell/node-spdy/README.md
+++ /dev/null
@@ -1,262 +0,0 @@
-# SPDY Server for node.js [![Build Status](https://secure.travis-ci.org/indutny/node-spdy.png)](http://travis-ci.org/indutny/node-spdy)
-
-<a href="http://flattr.com/thing/758213/indutnynode-spdy-on-GitHub" target="_blank">
-<img src="http://api.flattr.com/button/flattr-badge-large.png" alt="Flattr this" title="Flattr this" border="0" /></a>
-
-With this module you can create [SPDY](http://www.chromium.org/spdy) servers
-in node.js with natural http module interface and fallback to regular https
-(for browsers that don't support SPDY yet).
-
-## Usage
-
-Server:
-```javascript
-var spdy = require('spdy'),
-    fs = require('fs');
-
-var options = {
-  key: fs.readFileSync(__dirname + '/keys/spdy-key.pem'),
-  cert: fs.readFileSync(__dirname + '/keys/spdy-cert.pem'),
-  ca: fs.readFileSync(__dirname + '/keys/spdy-ca.pem'),
-
-  // **optional** SPDY-specific options
-  windowSize: 1024 * 1024, // Server's window size
-
-  // **optional** if true - server will send 3.1 frames on 3.0 *plain* spdy
-  autoSpdy31: false
-};
-
-var server = spdy.createServer(options, function(req, res) {
-  res.writeHead(200);
-  res.end('hello world!');
-});
-
-server.listen(3000);
-```
-
-Client:
-```javascript
-var spdy = require('spdy');
-var http = require('http');
-
-var agent = spdy.createAgent({
-  host: 'www.google.com',
-  port: 443,
-
-  // Optional SPDY options
-  spdy: {
-    plain: false or true,
-    ssl: false or true,
-    version: 3 // Force SPDY version
-  }
-});
-
-http.get({
-  host: 'www.google.com',
-  agent: agent
-}, function(response) {
-  console.log('yikes');
-  // Here it goes like with any other node.js HTTP request
-  // ...
-  // And once we're done - we may close TCP connection to server
-  // NOTE: All non-closed requests will die!
-  agent.close();
-}).end();
-```
-
-And by popular demand - usage with
-[express](https://github.com/visionmedia/express):
-
-```javascript
-var spdy = require('spdy'),
-    express = require('express'),
-    fs = require('fs');
-
-var options = { /* the same as above */ };
-
-var app = express();
-
-app.use(/* your favorite middleware */);
-
-var server = spdy.createServer(options, app);
-
-server.listen(3000);
-```
-
-## API
-
-API is compatible with `http` and `https` module, but you can use another
-function as base class for SPDYServer.
-
-```javascript
-spdy.createServer(
-  [base class constructor, i.e. https.Server],
-  { /* keys and options */ }, // <- the only one required argument
-  [request listener]
-).listen([port], [host], [callback]);
-```
-
-Request listener will receive two arguments: `request` and `response`. They're
-both instances of `http`'s `IncomingMessage` and `OutgoingMessage`. But three
-custom properties are added to both of them: `streamID`, `isSpdy`,
-`spdyVersion`. The first one indicates on which spdy stream are sitting request
-and response. Second is always true and can be checked to ensure that incoming
-request wasn't received by HTTPS fallback and last one is a number representing
-used SPDY protocol version (2 or 3 for now).
-
-### Push streams
-
-It is possible to initiate 'push' streams to send content to clients _before_
-the client requests it.
-
-```javascript
-spdy.createServer(options, function(req, res) {
-  var headers = { 'content-type': 'application/javascript' };
-  var stream = res.push('/main.js', headers);
-  stream.on('acknowledge', function() {
-  });
-  stream.on('error', function() {
-  });
-  stream.end('alert("hello from push stream!");');
-
-  res.end('<script src="/main.js"></script>');
-}).listen(3000);
-```
-
-The method is also avaliable when using SPDY with an Express server:
-
-```javascript
-var app = express();
-
-var server = spdy.createServer(options, app);
-
-app.get('/', function(req, res) {
-  var headers = { 'content-type': 'application/javascript' };
-  res.push('/main.js', headers, function(err, stream) {
-    stream.on('acknowledge', function() {
-    });
-
-    stream.on('error', function() {
-    });
-
-    stream.end('alert("hello from push stream!");');
-  });
-
-  res.end('<script src="/main.js"></script>');
-});
-
-server.listen(3000);
-```
-
-
-Push is accomplished via the `push()` method invoked on the current response
-object (this works for express.js response objects as well).  The format of the
-`push()` method is:
-
-`.push('full or relative url', { ... headers ... }, optional priority, callback)`
-
-You can use either full ( `http://host/path` ) or relative ( `/path` ) urls with
-`.push()`. `headers` are the same as for regular response object. `callback`
-will receive two arguments: `err` (if any error is happened) and `stream`
-(stream object have API compatible with a
-[net.Socket](http://nodejs.org/docs/latest/api/net.html#net.Socket) ).
-
-Client usage:
-```javascript
-var agent = spdy.createAgent({ /* ... */ });
-agent.on('push', function(stream) {
-  stream.on('error', function(err) {
-    // Handle error
-  });
-  // Read data from stream
-  // ...
-  // stream.associated points to associated client-initiated stream
-});
-```
-
-NOTE: You're responsible for the `stream` object once given it in `.push()`
-callback. Hence ignoring `error` events on it might result in uncaught
-exceptions and crash your program.
-
-### Trailing headers
-
-Server usage:
-```javascript
-function (req, res) {
-  // Send trailing headers to client
-  res.addTrailers({ header1: 'value1', header2: 'value2' });
-
-  // On client's trailing headers
-  req.on('trailers', function(headers) {
-    // ...
-  });
-}
-```
-
-Client usage:
-```javascript
-var req = http.request({ agent: spdyAgent, /* ... */ }).function (res) {
-  // On server's trailing headers
-  res.on('trailers', function(headers) {
-    // ...
-  });
-});
-req.write('stuff');
-req.addTrailers({ /* ... */ });
-req.end();
-```
-
-### Options
-
-All options supported by
-[tls](http://nodejs.org/docs/latest/api/tls.html#tls.createServer) are working
-with node-spdy. In addition, `maxStreams` options is available. it allows you
-controlling [maximum concurrent streams](http://www.chromium.org/spdy/spdy-protocol/spdy-protocol-draft2#TOC-SETTINGS)
-protocol option (if client will start more streams than that limit, RST_STREAM
-will be sent for each additional stream).
-
-Additional options:
-
-* `plain` - if defined, server will ignore NPN and ALPN data and choose whether
-  to use spdy or plain http by looking at first data packet.
-* `ssl` - if `false` and `options.plain` is `true`, `http.Server` will be used
-  as a `base` class for created server.
-* `maxChunk` - if set and non-falsy, limits number of bytes sent in one DATA
-  chunk. Setting it to non-zero value is recommended if you care about
-  interleaving of outgoing data from multiple different streams.
-  (defaults to 8192)
-
-#### Contributors
-
-* [Fedor Indutny](https://github.com/indutny)
-* [Chris Strom](https://github.com/eee-c)
-* [François de Metz](https://github.com/francois2metz)
-* [Ilya Grigorik](https://github.com/igrigorik)
-* [Roberto Peon](https://github.com/grmocg)
-* [Tatsuhiro Tsujikawa](https://github.com/tatsuhiro-t)
-* [Jesse Cravens](https://github.com/jessecravens)
-
-#### LICENSE
-
-This software is licensed under the MIT License.
-
-Copyright Fedor Indutny, 2014.
-
-Permission is hereby granted, free of charge, to any person obtaining a
-copy of this software and associated documentation files (the
-"Software"), to deal in the Software without restriction, including
-without limitation the rights to use, copy, modify, merge, publish,
-distribute, sublicense, and/or sell copies of the Software, and to permit
-persons to whom the Software is furnished to do so, subject to the
-following conditions:
-
-The above copyright notice and this permission notice shall be included
-in all copies or substantial portions of the Software.
-
-THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
-OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
-MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN
-NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,
-DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR
-OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE
-USE OR OTHER DEALINGS IN THE SOFTWARE.
deleted file mode 100644
--- a/testing/xpcshell/node-spdy/keys/spdy-cert.pem
+++ /dev/null
@@ -1,19 +0,0 @@
------BEGIN CERTIFICATE-----
-MIIDBjCCAe4CCQCC8qgopCwXKDANBgkqhkiG9w0BAQUFADBFMQswCQYDVQQGEwJB
-VTETMBEGA1UECBMKU29tZS1TdGF0ZTEhMB8GA1UEChMYSW50ZXJuZXQgV2lkZ2l0
-cyBQdHkgTHRkMB4XDTEzMDEwODEyMzYyM1oXDTIzMDEwNjEyMzYyM1owRTELMAkG
-A1UEBhMCQVUxEzARBgNVBAgTClNvbWUtU3RhdGUxITAfBgNVBAoTGEludGVybmV0
-IFdpZGdpdHMgUHR5IEx0ZDCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEB
-ALYWwPVTdWu+55Y9WKcZKi+iC/BVoV6uejF/7twOQZRAMAs2rFhCnxmds8d7jcX6
-wBHOejKFYqbm9WPORckieOVmHRHYLhzCXHrhYMHSYW5NxwTCxdka+QEzoFJqBSwO
-AkBQaF9ETA/GDa22TGN0DqUAtH6AiT3FAf4lSng1gLnMaa6+jYDmHmGHf2epRw+N
-U8Kb4g8iNLPP10M3x1DIlVtB2MvXgHFY5/fz4BSD8QweqUGaoIuAcLdJ6qJmbztm
-FWCWmr3uNHo2V6KxjHMMpziCa+280im6OgsdsgMuQO949hk+5k+PZ/WR+Ia4NylE
-FI6cVXpZwALAVWxC9VO1oocCAwEAATANBgkqhkiG9w0BAQUFAAOCAQEAluAKUeNS
-brX8+Jr7hOEftd+maTb8ERV4CU2wFSeCqupoSGh4Er37FO+eL1cAzaewpQzx8Uvp
-q7oO+utrOKGA42P0bkdX6vqXZ73seorKl4Mv6Lnq1z1uTRTQyAbvJpv6mYrr+oz5
-QgTGvPqUWqpv+OPf2R9J00IVLlfIjdKGLt0iZ3QEeS6SDkV/MHT4fEc9fImsg6Rq
-xcb8kmcv9GAHo7YzxOw2F85h93epl6zUUlW2QCzUbvEF2S5NQowdkDQz0py6o4tv
-S5Dh5XYLDm7gjcRElLNLaTmdhq9IGBEdbXy6a9kzJqZz4+AOn5+WPnA/KhVhWoTE
-nJHIzjR3CQEkbA==
------END CERTIFICATE-----
deleted file mode 100644
--- a/testing/xpcshell/node-spdy/keys/spdy-csr.pem
+++ /dev/null
@@ -1,16 +0,0 @@
------BEGIN CERTIFICATE REQUEST-----
-MIICijCCAXICAQAwRTELMAkGA1UEBhMCQVUxEzARBgNVBAgTClNvbWUtU3RhdGUx
-ITAfBgNVBAoTGEludGVybmV0IFdpZGdpdHMgUHR5IEx0ZDCCASIwDQYJKoZIhvcN
-AQEBBQADggEPADCCAQoCggEBALYWwPVTdWu+55Y9WKcZKi+iC/BVoV6uejF/7twO
-QZRAMAs2rFhCnxmds8d7jcX6wBHOejKFYqbm9WPORckieOVmHRHYLhzCXHrhYMHS
-YW5NxwTCxdka+QEzoFJqBSwOAkBQaF9ETA/GDa22TGN0DqUAtH6AiT3FAf4lSng1
-gLnMaa6+jYDmHmGHf2epRw+NU8Kb4g8iNLPP10M3x1DIlVtB2MvXgHFY5/fz4BSD
-8QweqUGaoIuAcLdJ6qJmbztmFWCWmr3uNHo2V6KxjHMMpziCa+280im6OgsdsgMu
-QO949hk+5k+PZ/WR+Ia4NylEFI6cVXpZwALAVWxC9VO1oocCAwEAAaAAMA0GCSqG
-SIb3DQEBBQUAA4IBAQCuMWhXWTpHDZTYFtkasd/b02D45RyyQTYNvw0qS67rBKnj
-52YvHKXvdjXe+TFuEzq6G7QAa7cgcdv12ffzboa8l9E4hY4OTO/lysCB1gMxgpTg
-ulDFRTQrIgCjrIm4rIGkFj47VL0ieSRhU4bf9npQydXdaYk0DHOxpLdGrs85LbZf
-lt/5Bsls9bSsh+JYcgoOPYxcgKBzhingh/FV93HQ39JHxtcqkrpZqrfNfHSVr9gT
-t+YyvUh0ctO5oGEfQj27Ewk3yt1nwgCETP55yCUhWIhJF5ATSFqm0nfeS1QYHMcU
-27Hcp+20/4D4MbZ04gi4bi6Z92DawssfKfow/B4u
------END CERTIFICATE REQUEST-----
deleted file mode 100644
--- a/testing/xpcshell/node-spdy/keys/spdy-key.pem
+++ /dev/null
@@ -1,27 +0,0 @@
------BEGIN RSA PRIVATE KEY-----
-MIIEowIBAAKCAQEAthbA9VN1a77nlj1YpxkqL6IL8FWhXq56MX/u3A5BlEAwCzas
-WEKfGZ2zx3uNxfrAEc56MoVipub1Y85FySJ45WYdEdguHMJceuFgwdJhbk3HBMLF
-2Rr5ATOgUmoFLA4CQFBoX0RMD8YNrbZMY3QOpQC0foCJPcUB/iVKeDWAucxprr6N
-gOYeYYd/Z6lHD41TwpviDyI0s8/XQzfHUMiVW0HYy9eAcVjn9/PgFIPxDB6pQZqg
-i4Bwt0nqomZvO2YVYJaave40ejZXorGMcwynOIJr7bzSKbo6Cx2yAy5A73j2GT7m
-T49n9ZH4hrg3KUQUjpxVelnAAsBVbEL1U7WihwIDAQABAoIBACdvHBDFJ0vTRzI5
-TOa7Q3CXZoCA+vaXUK1BqIgNqlQh5oW3LHHc07nndlTARD7ZBBmXHs2sJ2Y/5Grd
-9C0QAyCjEa6Yo7vkt8SA5MR0/Fa4D17Pk6tl9QE2ngTbIw2cZw5om4HuN46+9J1n
-OnnbW4SOd4hh69btwHW6u7r2007pQXme0AMlAxhgfIEiD6tHjqZDCtK4G0d+GSq6
-Ks/IpXckLcrluqJ2gHVB2sbBbjh1m7dHCVzBKynCwaHrWbNla8P6j3SdabP4Umcb
-tu3hP3nLigMJmA16KdkayUg05OvUTBAkReLcVZYZQ80LmM+NioB6UvwYy677h4ma
-XFihvLkCgYEA3aLOY2rve6DxvTXDJe8D91V//+5B9XBcyLP2cMEXIP+3W9Gto9tz
-vTIOcwj8MLKh22KBBMCP7OQlXFalBoG/d5Y9YKr6X2XHBcEw96Nm1HZctUPRPQdd
-+C8S5ikwTre9QMfLmLGKzgfIpDRYyijv0ZQZw+8qlNATtVrAMQGu6D0CgYEA0lI9
-zXK+4P28+SkkCUIG/Y31wF4KeM8V5s8eUYej8LV67GQIGs9XPCEIJY2cHZpn7qD8
-H90lucr90rwAHN2rLUSdq28NVL0+RTYKNBFRRvPNloLlKOR9RvorsFz5U4z48i9x
-yZ6gk+WL0ycc2oUFfihmQpHhRUiV46IB7deEXhMCgYEA1rW+3V8eC5VaOuOXXutS
-20vwCX7GVUB6ElENICRfBK/V8NSLM98IG7QffV+p+H9E/+RIetMVWveWHgMuMcSG
-ORLJ+RkKHlrZ2IBUsMKSfqb/nvbJACdf6GuqEmC6lLe5VsV3PkBY6MlvnWu8zHOm
-CFFCOKc8iBef0CPPZmpsCD0CgYAOtS+bOWX9x+C6L9VUTGi+vHmuDSWAU0L91AgT
-vX+KaraA53HlphA8pTazoZaEP3L7LgjTlZx4xKhBX2JGon3A+aZpAagV//Hl1ySZ
-hYiAhLYgy2CJHolgOEhr2eSZoicakJTNe6lRDmFbz8Vlxp2et+aGyzrMpInO1Fp8
-LnEUPwKBgExMk6THLz8CzjJhaKDrNn1fSs6jUxgK12+1cIJxb5JEgRJs4W+yFuLw
-exCE5YKPwnZNrbji+bdkk9FwHPLuf20aH5fIB0UlMMVcvLGKyxYl7BG1pShN4k8C
-kKXaClwkngJ2eSs/AsNAe9hhbEpFjAHt+3D7Sbg8EvgeCwdjnIxw
------END RSA PRIVATE KEY-----
deleted file mode 100644
--- a/testing/xpcshell/node-spdy/lib/spdy.js
+++ /dev/null
@@ -1,29 +0,0 @@
-var spdy = exports;
-
-// Exports utils
-spdy.utils = require('./spdy/utils');
-
-// Export parser&framer
-spdy.protocol = require('./spdy/protocol');
-
-// Export ServerResponse
-spdy.response = require('./spdy/response');
-
-// Export Scheduler
-spdy.scheduler = require('./spdy/scheduler');
-
-// Export ZlibPool
-spdy.zlibpool = require('./spdy/zlib-pool');
-
-// Export Connection and Stream
-spdy.Stream = require('./spdy/stream').Stream;
-spdy.Connection = require('./spdy/connection').Connection;
-
-// Export server
-spdy.server = require('./spdy/server');
-spdy.Server = spdy.server.Server;
-spdy.createServer = spdy.server.create;
-
-// Export client
-spdy.Agent = require('./spdy/client').Agent;
-spdy.createAgent = require('./spdy/client').create;
deleted file mode 100644
--- a/testing/xpcshell/node-spdy/lib/spdy/client.js
+++ /dev/null
@@ -1,230 +0,0 @@
-var spdy = require('../spdy');
-var assert = require('assert');
-var util = require('util');
-var net = require('net');
-var https = require('https');
-var EventEmitter = require('events').EventEmitter;
-
-var proto = {};
-
-function instantiate(base) {
-  function Agent(options) {
-    base.call(this, options);
-
-    if (!this.options.spdy)
-      this.options.spdy = {};
-
-    this._init();
-
-    // Hack for node.js v0.10
-    this.createConnection = proto.createConnection;
-
-    // No chunked encoding
-    this.keepAlive = false;
-  };
-  util.inherits(Agent, base);
-
-  // Copy prototype methods
-  Object.keys(proto).forEach(function(key) {
-    this[key] = proto[key];
-  }, Agent.prototype);
-
-  return Agent;
-};
-
-proto._init = function init() {
-  var self = this;
-
-  var state = {};
-  // Find super's `createConnection` method
-  var createConnection;
-  var cons = this.constructor.super_;
-  do {
-    createConnection = cons.prototype.createConnection;
-
-    if (cons.super_ === EventEmitter || !cons.super_)
-      break;
-    cons = cons.super_;
-  } while (!createConnection);
-
-  if (!createConnection)
-    createConnection = this.createConnection || net.createConnection;
-
-  // TODO(indutny): Think about falling back to http/https
-  var socket = createConnection.call(this, util._extend({
-    NPNProtocols: ['spdy/3.1', 'spdy/3', 'spdy/2'],
-    ALPNProtocols: ['spdy/3.1', 'spdy/3', 'spdy/2']
-  }, this.options));
-  state.socket = socket;
-
-  // Header compression is disabled by default in clients to prevent CRIME
-  // attacks. Don't enable it unless you know what you're doing.
-  if (this.options.spdy.headerCompression !== true)
-    this.options.spdy.headerCompression = false;
-
-  // Create SPDY connection using newly created socket
-  var connection = new spdy.Connection(socket,
-                                       util._extend(this.options.spdy, {
-    isServer: false
-  }));
-  state.connection = connection;
-
-  connection.on('error', function(err) {
-    self.emit('error', err);
-  });
-
-  // Select SPDY version
-  if (this.options.spdy.ssl !== false && !this.options.spdy.version) {
-    // SSL, wait for NPN or ALPN to happen
-    socket.once('secureConnect', function() {
-      var selectedProtocol = socket.npnProtocol || socket.alpnProtocol;
-      if (selectedProtocol === 'spdy/2')
-        connection._setVersion(2);
-      else if (selectedProtocol === 'spdy/3')
-        connection._setVersion(3);
-      else if (selectedProtocol === 'spdy/3.1')
-        connection._setVersion(3.1);
-      else
-        socket.emit('error', new Error('No supported SPDY version'));
-    });
-  } else {
-    // No SSL, use fixed version
-    connection._setVersion(this.options.spdy.version || 3);
-  }
-
-  // Destroy PUSH streams until the listener will be added
-  connection.on('stream', function(stream) {
-    stream.on('error', function() {});
-    stream.destroy();
-  });
-  state.pushServer = null;
-
-  this.on('newListener', this._onNewListener.bind(this));
-  this.on('removeListener', this._onRemoveListener.bind(this));
-
-  // Client has odd-numbered stream ids
-  state.id = 1;
-  this._spdyState = state;
-};
-
-//
-// ### function onNewListener (type, listener)
-// #### @type {String} Event type
-// #### @listener {Function} Listener callback
-//
-proto._onNewListener = function onNewListener(type, listener) {
-  if (type !== 'push')
-    return;
-
-  var state = this._spdyState;
-  if (state.pushServer)
-    return state.pushServer.on('translated-request', listener);
-
-  state.pushServer = require('http').createServer(listener);
-  state.connection.removeAllListeners('stream');
-  state.connection.on('stream', function(stream) {
-    state.pushServer.emit('connection', stream);
-  });
-
-  state.pushServer.on('request', function(req) {
-    // Populate trailing headers
-    req.connection.on('headers', function(headers) {
-      Object.keys(headers).forEach(function(key) {
-        req.trailers[key] = headers[key];
-      });
-      req.emit('trailers', headers);
-    });
-
-    this.emit('translated-request', req);
-  });
-};
-
-//
-// ### function onRemoveListener (type, listener)
-// #### @type {String} Event type
-// #### @listener {Function} Listener callback
-//
-proto._onRemoveListener = function onRemoveListener(type, listener) {
-  if (type !== 'push')
-    return;
-
-  var state = this._spdyState;
-  if (!state.pushServer)
-    return;
-
-  state.pushServer.removeListener('translated-request', listener);
-};
-
-//
-// ### function createConnection (options)
-//
-proto.createConnection = function createConnection(options) {
-  if (!options)
-    options = {};
-
-  var state = this._spdyState;
-  var stream = new spdy.Stream(state.connection, {
-    id: state.id,
-    priority: options.priority || 7,
-    client: true,
-    decompress: options.spdy.decompress == undefined ? true :
-                                                       options.spdy.decompress
-  });
-  state.id += 2;
-
-  return stream;
-};
-
-//
-// ### function close (callback)
-// #### @callback {Function}
-// Close underlying socket and terminate all streams
-//
-proto.close = function close(callback) {
-  this._spdyState.socket.destroySoon();
-  if (callback)
-    this._spdyState.socket.once('close', callback);
-};
-
-//
-// ### function ping (callback)
-// #### @callback {Function}
-// Send PING frame and invoke callback once received it back
-//
-proto.ping = function ping(callback) {
-  return this._spdyState.connection.ping(callback);
-};
-
-//
-// Default Agent
-//
-exports.Agent = instantiate(https.Agent);
-
-//
-// ### function create (base, options)
-// #### @base {Function} (optional) base server class (https.Server)
-// #### @options {Object} tls server options
-// @constructor wrapper
-//
-exports.create = function create(base, options) {
-  var agent;
-  if (typeof base === 'function') {
-    agent = instantiate(base);
-  } else {
-    agent = exports.Agent;
-
-    options = base;
-    base = null;
-  }
-
-  // Instantiate http server if `ssl: false`
-  if (!base &&
-      options &&
-      options.spdy &&
-      options.spdy.plain &&
-      options.spdy.ssl === false) {
-    return exports.create(require('http').Agent, options);
-  }
-
-  return new agent(options);
-};
deleted file mode 100644
--- a/testing/xpcshell/node-spdy/lib/spdy/connection.js
+++ /dev/null
@@ -1,648 +0,0 @@
-var util = require('util');
-var assert = require('assert');
-var spdy = require('../spdy');
-var constants = spdy.protocol.constants;
-
-var Stream = spdy.Stream;
-
-//
-// ### function Connection (socket, state, server)
-// #### @socket {net.Socket} server's connection
-// #### @options {Object} Connection options
-// #### @server {net.Server} server
-// Abstract connection @constructor
-//
-function Connection(socket, options, server) {
-  process.EventEmitter.call(this);
-
-  var state = {};
-  this._spdyState = state;
-
-  // NOTE: There's a big trick here. Connection is used as a `this` argument
-  // to the wrapped `connection` event listener.
-  // socket end doesn't necessarly mean connection drop
-  this.httpAllowHalfOpen = true;
-
-  // Socket timeout
-  this.timeout = server && server.timeout || 0;
-
-  // Defaults
-  state.maxStreams = options.maxStreams || Infinity;
-  state.initialSinkSize = constants.DEFAULT_WINDOW;
-  state.initialWindowSize = options.windowSize || 1 << 20;
-  state.autoSpdy31 = options.autoSpdy31;
-
-  // Connection-level flow control
-  state.sinkSize = state.initialSinkSize;
-  state.windowSize = constants.DEFAULT_WINDOW;
-
-  // Interleaving configuration
-  state.maxChunk = options.maxChunk === undefined ? 8 * 1024 : options.maxChunk;
-
-  // Various state info
-  state.closed = false;
-  state.pool = spdy.zlibpool.create(options.headerCompression);
-  state.counters = {
-    pushCount: 0,
-    streamCount: 0
-  };
-  state.socketBuffering = false;
-
-  state.version = null;
-  state.deflate = null;
-  state.inflate = null;
-
-  // Init streams list
-  state.isServer = options.isServer;
-  state.streams = {};
-  state.streamCount = 0;
-  state.lastId = 0;
-  state.pushId = 0;
-  state.pingId = state.isServer ? 0 : 1;
-  state.pings = {};
-  state.goaway = false;
-
-  // X-Forwarded feature
-  state.xForward = null;
-
-  // Initialize scheduler
-  state.scheduler = spdy.scheduler.create(this);
-
-  // Create parser and hole for framer
-  state.parser = spdy.protocol.parser.create(this);
-  state.framer = spdy.protocol.framer.create();
-
-  // Lock data
-  state.locked = false;
-  state.lockQueue = [];
-
-  this.socket = socket;
-  this.encrypted = socket.encrypted;
-  this.readable = true;
-  this.writable = true;
-
-  this._init();
-}
-util.inherits(Connection, process.EventEmitter);
-exports.Connection = Connection;
-
-Connection.prototype._init = function init() {
-  var self = this;
-  var state = this._spdyState;
-  var pool = state.pool;
-  var pair = null;
-  var sentSettings = false;
-
-  // Initialize parser
-  this._spdyState.parser.on('frame', this._handleFrame.bind(this));
-
-  this._spdyState.parser.on('version', function onversion(version) {
-    var prev = state.version;
-    var framer = state.framer;
-
-    state.version = version;
-
-    // Ignore transition to 3.1
-    if (!prev) {
-      pair = pool.get('spdy/' + version);
-      state.deflate = pair.deflate;
-      state.inflate = pair.inflate;
-      framer.setCompression(pair.deflate, pair.inflate);
-    }
-    framer.setVersion(version);
-
-    // Send settings frame (once)
-    if (!sentSettings) {
-      sentSettings = true;
-      framer.settingsFrame({
-        maxStreams: state.maxStreams,
-        windowSize: state.initialWindowSize
-      }, function(err, frame) {
-        if (err)
-          return self.emit('error', err);
-        self.write(frame);
-      });
-
-      // Send WINDOW_UPDATE for 3.1
-      self._sendWindowUpdate(true);
-    }
-  });
-
-  // Propagate parser errors
-  state.parser.on('error', function onParserError(err) {
-    self.emit('error', err);
-  });
-
-  this.socket.pipe(state.parser);
-
-  // 2 minutes socket timeout
-  this.socket.setTimeout(this.timeout);
-  this.socket.once('timeout', function ontimeout() {
-    self.socket.destroy();
-  });
-
-  // Allow high-level api to catch socket errors
-  this.socket.on('error', function onSocketError(e) {
-    self.emit('error', e);
-  });
-
-  this.socket.once('close', function onclose() {
-    var err = new Error('socket hang up');
-    err.code = 'ECONNRESET';
-    self._destroyStreams(err);
-    self.emit('close');
-
-    state.closed = true;
-    if (pair)
-      pool.put(pair);
-  });
-
-  // Do not allow half-open connections
-  this.socket.allowHalfOpen = false;
-
-  if (spdy.utils.isLegacy) {
-    this.socket.on('drain', function ondrain() {
-      self.emit('drain');
-    });
-  }
-
-  // for both legacy and non-legacy, when our socket is ready for writes again,
-  //   drain the sinks in case they were queuing due to socketBuffering.
-  this.socket.on('drain', function () {
-    if (!state.socketBuffering)
-      return;
-
-    state.socketBuffering = false;
-    Object.keys(state.streams).forEach(function(id) {
-      state.streams[id]._drainSink(0);
-    });
-  });
-};
-
-//
-// ### function handleFrame (frame)
-// #### @frame {Object} SPDY frame
-//
-Connection.prototype._handleFrame = function handleFrame(frame) {
-  var state = this._spdyState;
-
-  if (state.closed)
-    return;
-
-  var stream;
-
-  // Create new stream
-  if (frame.type === 'SYN_STREAM') {
-    stream = this._handleSynStream(frame);
-  } else {
-    if (frame.id !== undefined) {
-      // Load created one
-      stream = state.streams[frame.id];
-
-      // Fail if not found
-      if (stream === undefined &&
-          !(frame.type === 'WINDOW_UPDATE' && frame.id === 0)) {
-        if (frame.type === 'RST_STREAM')
-          return;
-        this._rst(frame.id, constants.rst.INVALID_STREAM);
-        return;
-      }
-    }
-
-    // Emit 'data' event
-    if (frame.type === 'DATA') {
-      this._handleData(stream, frame);
-    // Reply for client stream
-    } else if (frame.type === 'SYN_REPLY') {
-      // If stream not client - send RST
-      if (!stream._spdyState.isClient) {
-        this._rst(frame.id, constants.rst.PROTOCOL_ERROR);
-        return;
-      }
-
-      stream._handleResponse(frame);
-
-    // Destroy stream if we were asked to do this
-    } else if (frame.type === 'RST_STREAM') {
-      stream._spdyState.rstCode = 0;
-      stream._spdyState.closedBy.us = true;
-      stream._spdyState.closedBy.them = true;
-
-      // Emit error on destroy
-      var err = new Error('Received rst: ' + frame.status);
-      err.code = 'RST_STREAM';
-      err.status = frame.status;
-      stream.destroy(err);
-    // Respond with same PING
-    } else if (frame.type === 'PING') {
-      this._handlePing(frame.pingId);
-    } else if (frame.type === 'SETTINGS') {
-      this._setDefaultWindow(frame.settings);
-    } else if (frame.type === 'GOAWAY') {
-      state.goaway = frame.lastId;
-      this.writable = false;
-    } else if (frame.type === 'WINDOW_UPDATE') {
-      if (stream)
-        stream._drainSink(frame.delta);
-      else
-        this._drainSink(frame.delta);
-    } else if (frame.type === 'HEADERS') {
-      stream.emit('headers', frame.headers);
-    } else if (frame.type === 'X_FORWARDED') {
-      state.xForward = frame.host;
-    } else {
-      console.error('Unknown type: ', frame.type);
-    }
-  }
-
-  // Handle half-closed
-  if (frame.fin) {
-    // Don't allow to close stream twice
-    if (stream._spdyState.closedBy.them) {
-      stream._spdyState.rstCode = constants.rst.PROTOCOL_ERROR;
-      stream.emit('error', 'Already half-closed');
-    } else {
-      stream._spdyState.closedBy.them = true;
-
-      // Receive FIN
-      stream._recvEnd();
-
-      stream._handleClose();
-    }
-  }
-};
-
-//
-// ### function handleSynStream (frame)
-// #### @frame {Object} SPDY frame
-//
-Connection.prototype._handleSynStream = function handleSynStream(frame) {
-  var state = this._spdyState;
-  var associated;
-
-  if (state.goaway && state.goaway < frame.id)
-    return this._rst(frame.id, constants.rst.REFUSED_STREAM);
-
-  // PUSH stream
-  if (!state.isServer) {
-    // Incorrect frame id
-    if (frame.id % 2 === 1 || frame.associated % 2 === 0)
-      return this._rst(frame.id, constants.rst.PROTOCOL_ERROR);
-
-    associated = state.streams[frame.associated];
-
-    // Fail if not found
-    if (associated === undefined) {
-      if (frame.type === 'RST_STREAM')
-        return;
-      this._rst(frame.id, constants.rst.INVALID_STREAM);
-      return;
-    }
-  }
-
-  var stream = new Stream(this, frame);
-
-  // Associate streams
-  if (associated) {
-    stream.associated = associated;
-  }
-
-  // TODO(indutny) handle stream limit
-  this.emit('stream', stream);
-  stream._start(frame.url, frame.headers);
-
-  return stream;
-};
-
-//
-// ### function _handleData (stream, frame)
-// #### @stream {Stream} SPDY Stream
-// #### @frame {Object} SPDY frame
-//
-Connection.prototype._handleData = function handleData(stream, frame) {
-  var state = this._spdyState;
-
-  if (frame.data.length > 0) {
-    if (stream._spdyState.closedBy.them) {
-      stream._spdyState.rstCode = constants.rst.PROTOCOL_ERROR;
-      stream.emit('error', 'Writing to half-closed stream');
-    } else {
-      // Connection-level flow control
-      state.windowSize -= frame.data.length;
-      this._sendWindowUpdate();
-      stream._recv(frame.data);
-    }
-  }
-};
-
-//
-// ### function sendWindowUpdate (force)
-// #### @force {Boolean} send even if windowSize is positive
-// Send WINDOW_UPDATE if needed
-//
-Connection.prototype._sendWindowUpdate = function sendWindowUpdate(force) {
-  var state = this._spdyState;
-
-  if (state.version < 3.1 && (!state.isServer || !state.autoSpdy31) ||
-      state.windowSize > state.initialWindowSize / 2 && !force) {
-    return;
-  }
-
-  var self = this;
-  var delta = state.initialWindowSize - state.windowSize;
-  if (delta === 0)
-    return;
-
-  state.windowSize += delta;
-  state.framer.windowUpdateFrame(0, delta, function(err, frame) {
-    if (err)
-      return self.emit('error', err);
-    self.write(frame);
-  });
-};
-
-//
-// ### function _drainSink (delta)
-// #### @delta {Number} WINDOW_UPDATE delta value
-//
-Connection.prototype._drainSink = function drainSink(delta) {
-  var state = this._spdyState;
-
-  // Switch to 3.1
-  if (state.version !== 3.1) {
-    this._setVersion(3.1);
-    this._sendWindowUpdate();
-  }
-
-  state.sinkSize += delta;
-
-  if (state.sinkSize <= 0)
-    return;
-
-  this.emit('drain');
-
-  // Try to write all pending data to the socket
-  Object.keys(state.streams).forEach(function(id) {
-    state.streams[id]._drainSink(0);
-  });
-};
-
-//
-// ### function setVersion (version)
-// #### @version {Number} Protocol version
-// Set protocol version to use
-//
-Connection.prototype._setVersion = function setVersion(version) {
-  this._spdyState.parser.setVersion(version);
-};
-
-//
-// ### function addStream (stream)
-// #### @stream {Stream}
-//
-Connection.prototype._addStream = function addStream(stream) {
-  var state = this._spdyState;
-  var id = stream._spdyState.id;
-  if (state.streams[id])
-    return;
-  state.streams[id] = stream;
-
-  // Update lastId
-  state.lastId = Math.max(state.lastId, id);
-
-  var isClient = id % 2 == 1;
-  if (isClient && state.isServer || !isClient && !state.isServer)
-    state.streamCount++;
-};
-
-//
-// ### function removeStream (stream)
-// #### @stream {Stream}
-//
-Connection.prototype._removeStream = function removeStream(stream) {
-  var state = this._spdyState;
-  var id = stream._spdyState.id;
-  if (!state.streams[id])
-    return;
-
-  delete state.streams[id];
-
-  var isClient = id % 2 == 1;
-  if (isClient && state.isServer || !isClient && !state.isServer)
-    state.streamCount--;
-
-  if (!state.isServer &&
-      state.goaway &&
-      state.streamCount === 0 &&
-      this.socket) {
-    this.socket.destroySoon();
-  }
-};
-
-//
-// ### function destroyStreams (err)
-// #### @err {Error} *optional*
-// Destroys all active streams
-//
-Connection.prototype._destroyStreams = function destroyStreams(err) {
-  var state = this._spdyState;
-  var streams = state.streams;
-  state.streams = {};
-  state.streamCount = 0;
-  Object.keys(streams).forEach(function(id) {
-    streams[id].destroy();
-  });
-};
-
-//
-// ### function _rst (streamId, code, extra)
-// #### @streamId {Number}
-// #### @code {Number}
-// #### @extra {String}
-// Send RST frame
-//
-Connection.prototype._rst = function rst(streamId, code, extra) {
-  var self = this;
-  this._spdyState.framer.rstFrame(streamId, code, extra, function(err, frame) {
-    if (err)
-      return self.emit('error', err);
-    self.write(frame);
-  });
-};
-
-//
-// ### function lock (callback)
-// #### @callback {Function} continuation callback
-// Acquire lock
-//
-Connection.prototype._lock = function lock(callback) {
-  if (!callback)
-    return;
-
-  var state = this._spdyState;
-  if (state.locked) {
-    state.lockQueue.push(callback);
-  } else {
-    state.locked = true;
-    callback(null);
-  }
-};
-
-//
-// ### function unlock ()
-// Release lock and call all buffered callbacks
-//
-Connection.prototype._unlock = function unlock() {
-  var state = this._spdyState;
-  if (state.locked) {
-    if (state.lockQueue.length) {
-      var cb = state.lockQueue.shift();
-      cb(null);
-    } else {
-      state.locked = false;
-    }
-  }
-};
-
-//
-// ### function write (data, encoding)
-// #### @data {String|Buffer} data
-// #### @encoding {String} (optional) encoding
-// Writes data to socket
-//
-Connection.prototype.write = function write(data, encoding) {
-  if (this.socket.writable) {
-    var wroteThrough = this.socket.write(data, encoding);
-    // if write returns false, the socket layer is buffering the data, so let's
-    //   set a flag that we can use to create some backpressure
-    if (!wroteThrough)
-      this._spdyState.socketBuffering = true;
-    return wroteThrough;
-  }
-};
-
-//
-// ### function _setDefaultWindow (settings)
-// #### @settings {Object}
-// Update the default transfer window -- in the connection and in the
-// active streams
-//
-Connection.prototype._setDefaultWindow = function _setDefaultWindow(settings) {
-  if (!settings)
-    return;
-  if (!settings.initial_window_size ||
-      settings.initial_window_size.persisted) {
-    return;
-  }
-  var state = this._spdyState;
-  state.initialSinkSize = settings.initial_window_size.value;
-
-  Object.keys(state.streams).forEach(function(id) {
-    state.streams[id]._updateSinkSize(settings.initial_window_size.value);
-  });
-};
-
-//
-// ### function handlePing (id)
-// #### @id {Number} PING id
-//
-Connection.prototype._handlePing = function handlePing(id) {
-  var self = this;
-  var state = this._spdyState;
-
-  var ours = state.isServer && (id % 2 === 0) ||
-             !state.isServer && (id % 2 === 1);
-
-  // Handle incoming PING
-  if (!ours) {
-    state.framer.pingFrame(id, function(err, frame) {
-      if (err)
-        return self.emit('error', err);
-
-      self.emit('ping', id);
-      self.write(frame);
-    });
-    return;
-  }
-
-  // Handle reply PING
-  if (!state.pings[id])
-    return;
-  var ping = state.pings[id];
-  delete state.pings[id];
-
-  if (ping.cb)
-    ping.cb(null);
-};
-
-//
-// ### function ping (callback)
-// #### @callback {Function}
-// Send PING frame and invoke callback once received it back
-//
-Connection.prototype.ping = function ping(callback) {
-  var self = this;
-  var state = this._spdyState;
-  var id = state.pingId;
-
-  state.pingId += 2;
-
-  state.framer.pingFrame(id, function(err, frame) {
-    if (err)
-      return self.emit('error', err);
-
-    state.pings[id] = { cb: callback };
-    self.write(frame);
-  });
-};
-
-//
-// ### function getCounter (name)
-// #### @name {String} Counter name
-// Get counter value
-//
-Connection.prototype.getCounter = function getCounter(name) {
-  return this._spdyState.counters[name];
-};
-
-//
-// ### function cork ()
-// Accumulate data before writing out
-//
-Connection.prototype.cork = function cork() {
-  if (this.socket && this.socket.cork)
-    this.socket.cork();
-};
-
-//
-// ### function uncork ()
-// Write out accumulated data
-//
-Connection.prototype.uncork = function uncork() {
-  if (this.socket && this.socket.uncork)
-    this.socket.uncork();
-};
-
-Connection.prototype.end = function end() {
-  var self = this;
-  var state = this._spdyState;
-
-  state.framer.goawayFrame(state.lastId,
-                           constants.goaway.OK,
-                           function(err, frame) {
-    if (err)
-      return self.emit('error', err);
-
-    self.write(frame, function() {
-      state.goaway = state.lastId;
-
-      // Destroy socket if there are no streams
-      if (!state.isServer &&
-          state.goaway &&
-          state.streamCount === 0 &&
-          self.socket) {
-        self.socket.destroySoon();
-      }
-    });
-  });
-};
deleted file mode 100644
--- a/testing/xpcshell/node-spdy/lib/spdy/protocol/constants.js
+++ /dev/null
@@ -1,35 +0,0 @@
-exports.rst = {
-  PROTOCOL_ERROR: 1,
-  INVALID_STREAM: 2,
-  REFUSED_STREAM: 3,
-  UNSUPPORTED_VERSION: 4,
-  CANCEL: 5,
-  INTERNAL_ERROR: 6,
-  FLOW_CONTROL_ERROR: 7,
-  STREAM_IN_USE: 8,
-  STREAM_ALREADY_CLOSED: 9,
-  INVALID_CREDENTIALS: 10,
-  FRAME_TOO_LARGE: 11
-};
-
-exports.settings = {
-  FLAG_SETTINGS_PERSIST_VALUE: 1,
-  FLAG_SETTINGS_PERSISTED: 2,
-
-  SETTINGS_UPLOAD_BANDWIDTH: 1,
-  SETTINGS_DOWNLOAD_BANDWIDTH: 2,
-  SETTINGS_ROUND_TRIP_TIME: 3,
-  SETTINGS_MAX_CONCURRENT_STREAMS: 4,
-  SETTINGS_CURRENT_CWND: 5,
-  SETTINGS_DOWNLOAD_RETRANS_RATE: 6,
-  SETTINGS_INITIAL_WINDOW_SIZE: 7,
-  SETTINGS_CLIENT_CERTIFICATE_VECTOR_SIZE: 8
-};
-
-exports.DEFAULT_WINDOW = 64 * 1024;
-
-exports.goaway = {
-  OK: 0,
-  PROTOCOL_ERROR: 1,
-  INTERNAL_ERROR: 2
-};
deleted file mode 100644
--- a/testing/xpcshell/node-spdy/lib/spdy/protocol/dictionary.js
+++ /dev/null
@@ -1,203 +0,0 @@
-var Buffer = require('buffer').Buffer;
-
-var dictionary = {};
-module.exports = dictionary;
-
-dictionary[2] = new Buffer([
-  'optionsgetheadpostputdeletetraceacceptaccept-charsetaccept-encodingaccept-',
-  'languageauthorizationexpectfromhostif-modified-sinceif-matchif-none-matchi',
-  'f-rangeif-unmodifiedsincemax-forwardsproxy-authorizationrangerefererteuser',
-  '-agent10010120020120220320420520630030130230330430530630740040140240340440',
-  '5406407408409410411412413414415416417500501502503504505accept-rangesageeta',
-  'glocationproxy-authenticatepublicretry-afterservervarywarningwww-authentic',
-  'ateallowcontent-basecontent-encodingcache-controlconnectiondatetrailertran',
-  'sfer-encodingupgradeviawarningcontent-languagecontent-lengthcontent-locati',
-  'oncontent-md5content-rangecontent-typeetagexpireslast-modifiedset-cookieMo',
-  'ndayTuesdayWednesdayThursdayFridaySaturdaySundayJanFebMarAprMayJunJulAugSe',
-  'pOctNovDecchunkedtext/htmlimage/pngimage/jpgimage/gifapplication/xmlapplic',
-  'ation/xhtmltext/plainpublicmax-agecharset=iso-8859-1utf-8gzipdeflateHTTP/1',
-  '.1statusversionurl\x00'
-].join(''));
-
-dictionary[3] = new Buffer([
-  0x00, 0x00, 0x00, 0x07, 0x6f, 0x70, 0x74, 0x69,  // ....opti
-  0x6f, 0x6e, 0x73, 0x00, 0x00, 0x00, 0x04, 0x68,  // ons....h
-  0x65, 0x61, 0x64, 0x00, 0x00, 0x00, 0x04, 0x70,  // ead....p
-  0x6f, 0x73, 0x74, 0x00, 0x00, 0x00, 0x03, 0x70,  // ost....p
-  0x75, 0x74, 0x00, 0x00, 0x00, 0x06, 0x64, 0x65,  // ut....de
-  0x6c, 0x65, 0x74, 0x65, 0x00, 0x00, 0x00, 0x05,  // lete....
-  0x74, 0x72, 0x61, 0x63, 0x65, 0x00, 0x00, 0x00,  // trace...
-  0x06, 0x61, 0x63, 0x63, 0x65, 0x70, 0x74, 0x00,  // .accept.
-  0x00, 0x00, 0x0e, 0x61, 0x63, 0x63, 0x65, 0x70,  // ...accep
-  0x74, 0x2d, 0x63, 0x68, 0x61, 0x72, 0x73, 0x65,  // t-charse
-  0x74, 0x00, 0x00, 0x00, 0x0f, 0x61, 0x63, 0x63,  // t....acc
-  0x65, 0x70, 0x74, 0x2d, 0x65, 0x6e, 0x63, 0x6f,  // ept-enco
-  0x64, 0x69, 0x6e, 0x67, 0x00, 0x00, 0x00, 0x0f,  // ding....
-  0x61, 0x63, 0x63, 0x65, 0x70, 0x74, 0x2d, 0x6c,  // accept-l
-  0x61, 0x6e, 0x67, 0x75, 0x61, 0x67, 0x65, 0x00,  // anguage.
-  0x00, 0x00, 0x0d, 0x61, 0x63, 0x63, 0x65, 0x70,  // ...accep
-  0x74, 0x2d, 0x72, 0x61, 0x6e, 0x67, 0x65, 0x73,  // t-ranges
-  0x00, 0x00, 0x00, 0x03, 0x61, 0x67, 0x65, 0x00,  // ....age.
-  0x00, 0x00, 0x05, 0x61, 0x6c, 0x6c, 0x6f, 0x77,  // ...allow
-  0x00, 0x00, 0x00, 0x0d, 0x61, 0x75, 0x74, 0x68,  // ....auth
-  0x6f, 0x72, 0x69, 0x7a, 0x61, 0x74, 0x69, 0x6f,  // orizatio
-  0x6e, 0x00, 0x00, 0x00, 0x0d, 0x63, 0x61, 0x63,  // n....cac
-  0x68, 0x65, 0x2d, 0x63, 0x6f, 0x6e, 0x74, 0x72,  // he-contr
-  0x6f, 0x6c, 0x00, 0x00, 0x00, 0x0a, 0x63, 0x6f,  // ol....co
-  0x6e, 0x6e, 0x65, 0x63, 0x74, 0x69, 0x6f, 0x6e,  // nnection
-  0x00, 0x00, 0x00, 0x0c, 0x63, 0x6f, 0x6e, 0x74,  // ....cont
-  0x65, 0x6e, 0x74, 0x2d, 0x62, 0x61, 0x73, 0x65,  // ent-base
-  0x00, 0x00, 0x00, 0x10, 0x63, 0x6f, 0x6e, 0x74,  // ....cont
-  0x65, 0x6e, 0x74, 0x2d, 0x65, 0x6e, 0x63, 0x6f,  // ent-enco
-  0x64, 0x69, 0x6e, 0x67, 0x00, 0x00, 0x00, 0x10,  // ding....
-  0x63, 0x6f, 0x6e, 0x74, 0x65, 0x6e, 0x74, 0x2d,  // content-
-  0x6c, 0x61, 0x6e, 0x67, 0x75, 0x61, 0x67, 0x65,  // language
-  0x00, 0x00, 0x00, 0x0e, 0x63, 0x6f, 0x6e, 0x74,  // ....cont
-  0x65, 0x6e, 0x74, 0x2d, 0x6c, 0x65, 0x6e, 0x67,  // ent-leng
-  0x74, 0x68, 0x00, 0x00, 0x00, 0x10, 0x63, 0x6f,  // th....co
-  0x6e, 0x74, 0x65, 0x6e, 0x74, 0x2d, 0x6c, 0x6f,  // ntent-lo
-  0x63, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x00, 0x00,  // cation..
-  0x00, 0x0b, 0x63, 0x6f, 0x6e, 0x74, 0x65, 0x6e,  // ..conten
-  0x74, 0x2d, 0x6d, 0x64, 0x35, 0x00, 0x00, 0x00,  // t-md5...
-  0x0d, 0x63, 0x6f, 0x6e, 0x74, 0x65, 0x6e, 0x74,  // .content
-  0x2d, 0x72, 0x61, 0x6e, 0x67, 0x65, 0x00, 0x00,  // -range..
-  0x00, 0x0c, 0x63, 0x6f, 0x6e, 0x74, 0x65, 0x6e,  // ..conten
-  0x74, 0x2d, 0x74, 0x79, 0x70, 0x65, 0x00, 0x00,  // t-type..
-  0x00, 0x04, 0x64, 0x61, 0x74, 0x65, 0x00, 0x00,  // ..date..
-  0x00, 0x04, 0x65, 0x74, 0x61, 0x67, 0x00, 0x00,  // ..etag..
-  0x00, 0x06, 0x65, 0x78, 0x70, 0x65, 0x63, 0x74,  // ..expect
-  0x00, 0x00, 0x00, 0x07, 0x65, 0x78, 0x70, 0x69,  // ....expi
-  0x72, 0x65, 0x73, 0x00, 0x00, 0x00, 0x04, 0x66,  // res....f
-  0x72, 0x6f, 0x6d, 0x00, 0x00, 0x00, 0x04, 0x68,  // rom....h
-  0x6f, 0x73, 0x74, 0x00, 0x00, 0x00, 0x08, 0x69,  // ost....i
-  0x66, 0x2d, 0x6d, 0x61, 0x74, 0x63, 0x68, 0x00,  // f-match.
-  0x00, 0x00, 0x11, 0x69, 0x66, 0x2d, 0x6d, 0x6f,  // ...if-mo
-  0x64, 0x69, 0x66, 0x69, 0x65, 0x64, 0x2d, 0x73,  // dified-s
-  0x69, 0x6e, 0x63, 0x65, 0x00, 0x00, 0x00, 0x0d,  // ince....
-  0x69, 0x66, 0x2d, 0x6e, 0x6f, 0x6e, 0x65, 0x2d,  // if-none-
-  0x6d, 0x61, 0x74, 0x63, 0x68, 0x00, 0x00, 0x00,  // match...
-  0x08, 0x69, 0x66, 0x2d, 0x72, 0x61, 0x6e, 0x67,  // .if-rang
-  0x65, 0x00, 0x00, 0x00, 0x13, 0x69, 0x66, 0x2d,  // e....if-
-  0x75, 0x6e, 0x6d, 0x6f, 0x64, 0x69, 0x66, 0x69,  // unmodifi
-  0x65, 0x64, 0x2d, 0x73, 0x69, 0x6e, 0x63, 0x65,  // ed-since
-  0x00, 0x00, 0x00, 0x0d, 0x6c, 0x61, 0x73, 0x74,  // ....last
-  0x2d, 0x6d, 0x6f, 0x64, 0x69, 0x66, 0x69, 0x65,  // -modifie
-  0x64, 0x00, 0x00, 0x00, 0x08, 0x6c, 0x6f, 0x63,  // d....loc
-  0x61, 0x74, 0x69, 0x6f, 0x6e, 0x00, 0x00, 0x00,  // ation...
-  0x0c, 0x6d, 0x61, 0x78, 0x2d, 0x66, 0x6f, 0x72,  // .max-for
-  0x77, 0x61, 0x72, 0x64, 0x73, 0x00, 0x00, 0x00,  // wards...
-  0x06, 0x70, 0x72, 0x61, 0x67, 0x6d, 0x61, 0x00,  // .pragma.
-  0x00, 0x00, 0x12, 0x70, 0x72, 0x6f, 0x78, 0x79,  // ...proxy
-  0x2d, 0x61, 0x75, 0x74, 0x68, 0x65, 0x6e, 0x74,  // -authent
-  0x69, 0x63, 0x61, 0x74, 0x65, 0x00, 0x00, 0x00,  // icate...
-  0x13, 0x70, 0x72, 0x6f, 0x78, 0x79, 0x2d, 0x61,  // .proxy-a
-  0x75, 0x74, 0x68, 0x6f, 0x72, 0x69, 0x7a, 0x61,  // uthoriza
-  0x74, 0x69, 0x6f, 0x6e, 0x00, 0x00, 0x00, 0x05,  // tion....
-  0x72, 0x61, 0x6e, 0x67, 0x65, 0x00, 0x00, 0x00,  // range...
-  0x07, 0x72, 0x65, 0x66, 0x65, 0x72, 0x65, 0x72,  // .referer
-  0x00, 0x00, 0x00, 0x0b, 0x72, 0x65, 0x74, 0x72,  // ....retr
-  0x79, 0x2d, 0x61, 0x66, 0x74, 0x65, 0x72, 0x00,  // y-after.
-  0x00, 0x00, 0x06, 0x73, 0x65, 0x72, 0x76, 0x65,  // ...serve
-  0x72, 0x00, 0x00, 0x00, 0x02, 0x74, 0x65, 0x00,  // r....te.
-  0x00, 0x00, 0x07, 0x74, 0x72, 0x61, 0x69, 0x6c,  // ...trail
-  0x65, 0x72, 0x00, 0x00, 0x00, 0x11, 0x74, 0x72,  // er....tr
-  0x61, 0x6e, 0x73, 0x66, 0x65, 0x72, 0x2d, 0x65,  // ansfer-e
-  0x6e, 0x63, 0x6f, 0x64, 0x69, 0x6e, 0x67, 0x00,  // ncoding.
-  0x00, 0x00, 0x07, 0x75, 0x70, 0x67, 0x72, 0x61,  // ...upgra
-  0x64, 0x65, 0x00, 0x00, 0x00, 0x0a, 0x75, 0x73,  // de....us
-  0x65, 0x72, 0x2d, 0x61, 0x67, 0x65, 0x6e, 0x74,  // er-agent
-  0x00, 0x00, 0x00, 0x04, 0x76, 0x61, 0x72, 0x79,  // ....vary
-  0x00, 0x00, 0x00, 0x03, 0x76, 0x69, 0x61, 0x00,  // ....via.
-  0x00, 0x00, 0x07, 0x77, 0x61, 0x72, 0x6e, 0x69,  // ...warni
-  0x6e, 0x67, 0x00, 0x00, 0x00, 0x10, 0x77, 0x77,  // ng....ww
-  0x77, 0x2d, 0x61, 0x75, 0x74, 0x68, 0x65, 0x6e,  // w-authen
-  0x74, 0x69, 0x63, 0x61, 0x74, 0x65, 0x00, 0x00,  // ticate..
-  0x00, 0x06, 0x6d, 0x65, 0x74, 0x68, 0x6f, 0x64,  // ..method
-  0x00, 0x00, 0x00, 0x03, 0x67, 0x65, 0x74, 0x00,  // ....get.
-  0x00, 0x00, 0x06, 0x73, 0x74, 0x61, 0x74, 0x75,  // ...statu
-  0x73, 0x00, 0x00, 0x00, 0x06, 0x32, 0x30, 0x30,  // s....200
-  0x20, 0x4f, 0x4b, 0x00, 0x00, 0x00, 0x07, 0x76,  // .OK....v
-  0x65, 0x72, 0x73, 0x69, 0x6f, 0x6e, 0x00, 0x00,  // ersion..
-  0x00, 0x08, 0x48, 0x54, 0x54, 0x50, 0x2f, 0x31,  // ..HTTP.1
-  0x2e, 0x31, 0x00, 0x00, 0x00, 0x03, 0x75, 0x72,  // .1....ur
-  0x6c, 0x00, 0x00, 0x00, 0x06, 0x70, 0x75, 0x62,  // l....pub
-  0x6c, 0x69, 0x63, 0x00, 0x00, 0x00, 0x0a, 0x73,  // lic....s
-  0x65, 0x74, 0x2d, 0x63, 0x6f, 0x6f, 0x6b, 0x69,  // et-cooki
-  0x65, 0x00, 0x00, 0x00, 0x0a, 0x6b, 0x65, 0x65,  // e....kee
-  0x70, 0x2d, 0x61, 0x6c, 0x69, 0x76, 0x65, 0x00,  // p-alive.
-  0x00, 0x00, 0x06, 0x6f, 0x72, 0x69, 0x67, 0x69,  // ...origi
-  0x6e, 0x31, 0x30, 0x30, 0x31, 0x30, 0x31, 0x32,  // n1001012
-  0x30, 0x31, 0x32, 0x30, 0x32, 0x32, 0x30, 0x35,  // 01202205
-  0x32, 0x30, 0x36, 0x33, 0x30, 0x30, 0x33, 0x30,  // 20630030
-  0x32, 0x33, 0x30, 0x33, 0x33, 0x30, 0x34, 0x33,  // 23033043
-  0x30, 0x35, 0x33, 0x30, 0x36, 0x33, 0x30, 0x37,  // 05306307
-  0x34, 0x30, 0x32, 0x34, 0x30, 0x35, 0x34, 0x30,  // 40240540
-  0x36, 0x34, 0x30, 0x37, 0x34, 0x30, 0x38, 0x34,  // 64074084
-  0x30, 0x39, 0x34, 0x31, 0x30, 0x34, 0x31, 0x31,  // 09410411
-  0x34, 0x31, 0x32, 0x34, 0x31, 0x33, 0x34, 0x31,  // 41241341
-  0x34, 0x34, 0x31, 0x35, 0x34, 0x31, 0x36, 0x34,  // 44154164
-  0x31, 0x37, 0x35, 0x30, 0x32, 0x35, 0x30, 0x34,  // 17502504
-  0x35, 0x30, 0x35, 0x32, 0x30, 0x33, 0x20, 0x4e,  // 505203.N
-  0x6f, 0x6e, 0x2d, 0x41, 0x75, 0x74, 0x68, 0x6f,  // on-Autho
-  0x72, 0x69, 0x74, 0x61, 0x74, 0x69, 0x76, 0x65,  // ritative
-  0x20, 0x49, 0x6e, 0x66, 0x6f, 0x72, 0x6d, 0x61,  // .Informa
-  0x74, 0x69, 0x6f, 0x6e, 0x32, 0x30, 0x34, 0x20,  // tion204.
-  0x4e, 0x6f, 0x20, 0x43, 0x6f, 0x6e, 0x74, 0x65,  // No.Conte
-  0x6e, 0x74, 0x33, 0x30, 0x31, 0x20, 0x4d, 0x6f,  // nt301.Mo
-  0x76, 0x65, 0x64, 0x20, 0x50, 0x65, 0x72, 0x6d,  // ved.Perm
-  0x61, 0x6e, 0x65, 0x6e, 0x74, 0x6c, 0x79, 0x34,  // anently4
-  0x30, 0x30, 0x20, 0x42, 0x61, 0x64, 0x20, 0x52,  // 00.Bad.R
-  0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x34, 0x30,  // equest40
-  0x31, 0x20, 0x55, 0x6e, 0x61, 0x75, 0x74, 0x68,  // 1.Unauth
-  0x6f, 0x72, 0x69, 0x7a, 0x65, 0x64, 0x34, 0x30,  // orized40
-  0x33, 0x20, 0x46, 0x6f, 0x72, 0x62, 0x69, 0x64,  // 3.Forbid
-  0x64, 0x65, 0x6e, 0x34, 0x30, 0x34, 0x20, 0x4e,  // den404.N
-  0x6f, 0x74, 0x20, 0x46, 0x6f, 0x75, 0x6e, 0x64,  // ot.Found
-  0x35, 0x30, 0x30, 0x20, 0x49, 0x6e, 0x74, 0x65,  // 500.Inte
-  0x72, 0x6e, 0x61, 0x6c, 0x20, 0x53, 0x65, 0x72,  // rnal.Ser
-  0x76, 0x65, 0x72, 0x20, 0x45, 0x72, 0x72, 0x6f,  // ver.Erro
-  0x72, 0x35, 0x30, 0x31, 0x20, 0x4e, 0x6f, 0x74,  // r501.Not
-  0x20, 0x49, 0x6d, 0x70, 0x6c, 0x65, 0x6d, 0x65,  // .Impleme
-  0x6e, 0x74, 0x65, 0x64, 0x35, 0x30, 0x33, 0x20,  // nted503.
-  0x53, 0x65, 0x72, 0x76, 0x69, 0x63, 0x65, 0x20,  // Service.
-  0x55, 0x6e, 0x61, 0x76, 0x61, 0x69, 0x6c, 0x61,  // Unavaila
-  0x62, 0x6c, 0x65, 0x4a, 0x61, 0x6e, 0x20, 0x46,  // bleJan.F
-  0x65, 0x62, 0x20, 0x4d, 0x61, 0x72, 0x20, 0x41,  // eb.Mar.A
-  0x70, 0x72, 0x20, 0x4d, 0x61, 0x79, 0x20, 0x4a,  // pr.May.J
-  0x75, 0x6e, 0x20, 0x4a, 0x75, 0x6c, 0x20, 0x41,  // un.Jul.A
-  0x75, 0x67, 0x20, 0x53, 0x65, 0x70, 0x74, 0x20,  // ug.Sept.
-  0x4f, 0x63, 0x74, 0x20, 0x4e, 0x6f, 0x76, 0x20,  // Oct.Nov.
-  0x44, 0x65, 0x63, 0x20, 0x30, 0x30, 0x3a, 0x30,  // Dec.00.0
-  0x30, 0x3a, 0x30, 0x30, 0x20, 0x4d, 0x6f, 0x6e,  // 0.00.Mon
-  0x2c, 0x20, 0x54, 0x75, 0x65, 0x2c, 0x20, 0x57,  // ..Tue..W
-  0x65, 0x64, 0x2c, 0x20, 0x54, 0x68, 0x75, 0x2c,  // ed..Thu.
-  0x20, 0x46, 0x72, 0x69, 0x2c, 0x20, 0x53, 0x61,  // .Fri..Sa
-  0x74, 0x2c, 0x20, 0x53, 0x75, 0x6e, 0x2c, 0x20,  // t..Sun..
-  0x47, 0x4d, 0x54, 0x63, 0x68, 0x75, 0x6e, 0x6b,  // GMTchunk
-  0x65, 0x64, 0x2c, 0x74, 0x65, 0x78, 0x74, 0x2f,  // ed.text.
-  0x68, 0x74, 0x6d, 0x6c, 0x2c, 0x69, 0x6d, 0x61,  // html.ima
-  0x67, 0x65, 0x2f, 0x70, 0x6e, 0x67, 0x2c, 0x69,  // ge.png.i
-  0x6d, 0x61, 0x67, 0x65, 0x2f, 0x6a, 0x70, 0x67,  // mage.jpg
-  0x2c, 0x69, 0x6d, 0x61, 0x67, 0x65, 0x2f, 0x67,  // .image.g
-  0x69, 0x66, 0x2c, 0x61, 0x70, 0x70, 0x6c, 0x69,  // if.appli
-  0x63, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x2f, 0x78,  // cation.x
-  0x6d, 0x6c, 0x2c, 0x61, 0x70, 0x70, 0x6c, 0x69,  // ml.appli
-  0x63, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x2f, 0x78,  // cation.x
-  0x68, 0x74, 0x6d, 0x6c, 0x2b, 0x78, 0x6d, 0x6c,  // html.xml
-  0x2c, 0x74, 0x65, 0x78, 0x74, 0x2f, 0x70, 0x6c,  // .text.pl
-  0x61, 0x69, 0x6e, 0x2c, 0x74, 0x65, 0x78, 0x74,  // ain.text
-  0x2f, 0x6a, 0x61, 0x76, 0x61, 0x73, 0x63, 0x72,  // .javascr
-  0x69, 0x70, 0x74, 0x2c, 0x70, 0x75, 0x62, 0x6c,  // ipt.publ
-  0x69, 0x63, 0x70, 0x72, 0x69, 0x76, 0x61, 0x74,  // icprivat
-  0x65, 0x6d, 0x61, 0x78, 0x2d, 0x61, 0x67, 0x65,  // emax-age
-  0x3d, 0x67, 0x7a, 0x69, 0x70, 0x2c, 0x64, 0x65,  // .gzip.de
-  0x66, 0x6c, 0x61, 0x74, 0x65, 0x2c, 0x73, 0x64,  // flate.sd
-  0x63, 0x68, 0x63, 0x68, 0x61, 0x72, 0x73, 0x65,  // chcharse
-  0x74, 0x3d, 0x75, 0x74, 0x66, 0x2d, 0x38, 0x63,  // t.utf-8c
-  0x68, 0x61, 0x72, 0x73, 0x65, 0x74, 0x3d, 0x69,  // harset.i
-  0x73, 0x6f, 0x2d, 0x38, 0x38, 0x35, 0x39, 0x2d,  // so-8859-
-  0x31, 0x2c, 0x75, 0x74, 0x66, 0x2d, 0x2c, 0x2a,  // 1.utf-..
-  0x2c, 0x65, 0x6e, 0x71, 0x3d, 0x30, 0x2e         // .enq.0.
-]);
-
-dictionary[3.1] = dictionary[3];
deleted file mode 100644
--- a/testing/xpcshell/node-spdy/lib/spdy/protocol/framer.js
+++ /dev/null
@@ -1,497 +0,0 @@
-var spdy = require('../../spdy');
-var util = require('util');
-var Buffer = require('buffer').Buffer;
-var EventEmitter = require('events').EventEmitter;
-var constants = require('./').constants;
-
-var empty = new Buffer(0);
-
-function Framer() {
-  EventEmitter.call(this);
-
-  this.version = null;
-  this.deflate = null;
-  this.inflate = null;
-  this.debug = false;
-};
-util.inherits(Framer, EventEmitter);
-module.exports = Framer;
-
-Framer.create = function create(version, deflate, inflate) {
-  return new Framer(version, deflate, inflate);
-};
-
-//
-// ### function setCompression (deflate, inflate)
-// #### @deflate {Deflate}
-// #### @inflate {Inflate}
-// Set framer compression
-//
-Framer.prototype.setCompression = function setCompresion(deflate, inflate) {
-  this.deflate = spdy.utils.zwrap(deflate);
-  this.inflate = spdy.utils.zwrap(inflate);
-};
-
-
-//
-// ### function setCompression (deflate, inflate)
-// #### @deflate {Deflate}
-// #### @inflate {Inflate}
-// Set framer compression
-//
-Framer.prototype.setVersion = function setVersion(version) {
-  this.version = version;
-  this.emit('version');
-};
-
-//
-// internal, converts object into spdy dictionary
-//
-Framer.prototype.headersToDict = function headersToDict(headers, preprocess) {
-  function stringify(value) {
-    if (value !== undefined) {
-      if (Array.isArray(value)) {
-        return value.join('\x00');
-      } else if (typeof value === 'string') {
-        return value;
-      } else {
-        return value.toString();
-      }
-    } else {
-      return '';
-    }
-  }
-
-  // Lower case of all headers keys
-  var loweredHeaders = {};
-  Object.keys(headers || {}).map(function(key) {
-    loweredHeaders[key.toLowerCase()] = headers[key];
-  });
-
-  // Allow outer code to add custom headers or remove something
-  if (preprocess)
-    preprocess(loweredHeaders);
-
-  // Transform object into kv pairs
-  var size = this.version === 2 ? 2 : 4,
-      len = size,
-      pairs = Object.keys(loweredHeaders).filter(function(key) {
-        var lkey = key.toLowerCase();
-        return lkey !== 'connection' && lkey !== 'keep-alive' &&
-               lkey !== 'proxy-connection' && lkey !== 'transfer-encoding';
-      }).map(function(key) {
-        var klen = Buffer.byteLength(key),
-            value = stringify(loweredHeaders[key]),
-            vlen = Buffer.byteLength(value);
-
-        len += size * 2 + klen + vlen;
-        return [klen, key, vlen, value];
-      }),
-      result = new Buffer(len);
-
-  if (this.version === 2)
-    result.writeUInt16BE(pairs.length, 0, true);
-  else
-    result.writeUInt32BE(pairs.length, 0, true);
-
-  var offset = size;
-  pairs.forEach(function(pair) {
-    // Write key length
-    if (this.version === 2)
-      result.writeUInt16BE(pair[0], offset, true);
-    else
-      result.writeUInt32BE(pair[0], offset, true);
-    // Write key
-    result.write(pair[1], offset + size);
-
-    offset += pair[0] + size;
-
-    // Write value length
-    if (this.version === 2)
-      result.writeUInt16BE(pair[2], offset, true);
-    else
-      result.writeUInt32BE(pair[2], offset, true);
-    // Write value
-    result.write(pair[3], offset + size);
-
-    offset += pair[2] + size;
-  }, this);
-
-  return result;
-};
-
-Framer.prototype._synFrame = function _synFrame(type,
-                                                id,
-                                                assoc,
-                                                priority,
-                                                dict,
-                                                callback) {
-  var self = this;
-
-  // Compress headers
-  this.deflate(dict, function (err, chunks, size) {
-    if (err)
-      return callback(err);
-
-    var offset = type === 'SYN_STREAM' ? 18 : self.version === 2 ? 14 : 12,
-        total = offset - 8 + size,
-        frame = new Buffer(offset + size);
-
-    // Control + Version
-    frame.writeUInt16BE(0x8000 | self.version, 0, true);
-    // Type
-    frame.writeUInt16BE(type === 'SYN_STREAM' ? 1 : 2, 2, true);
-    // Size
-    frame.writeUInt32BE(total & 0x00ffffff, 4, true);
-    // Stream ID
-    frame.writeUInt32BE(id & 0x7fffffff, 8, true);
-
-    if (type === 'SYN_STREAM') {
-      // Unidirectional
-      if (assoc !== 0)
-        frame[4] = 2;
-
-      // Associated Stream-ID
-      frame.writeUInt32BE(assoc & 0x7fffffff, 12, true);
-
-      // Priority
-      var priorityValue;
-      if (self.version === 2)
-        priorityValue = Math.max(Math.min(priority, 3), 0) << 6;
-      else
-        priorityValue = Math.max(Math.min(priority, 7), 0) << 5;
-      frame.writeUInt8(priorityValue, 16, true);
-    }
-
-    for (var i = 0; i < chunks.length; i++) {
-      chunks[i].copy(frame, offset);
-      offset += chunks[i].length;
-    }
-
-    callback(null, frame);
-  });
-};
-
-//
-// ### function replyFrame (id, code, reason, headers, callback)
-// #### @id {Number} Stream ID
-// #### @code {Number} HTTP Status Code
-// #### @reason {String} (optional)
-// #### @headers {Object|Array} (optional) HTTP headers
-// #### @callback {Function} Continuation function
-// Sends SYN_REPLY frame
-//
-Framer.prototype.replyFrame = function replyFrame(id,
-                                                  code,
-                                                  reason,
-                                                  headers,
-                                                  callback) {
-  if (!this.version) {
-    return this.on('version', function() {
-      this.replyFrame(id, code, reason, headers, callback);
-    });
-  }
-
-  var self = this;
-  var dict = this.headersToDict(headers, function(headers) {
-    if (self.version === 2) {
-      headers.status = code + ' ' + reason;
-      headers.version = 'HTTP/1.1';
-    } else {
-      headers[':status'] = code + ' ' + reason;
-      headers[':version'] = 'HTTP/1.1';
-    }
-  });
-
-
-  this._synFrame('SYN_REPLY', id, null, 0, dict, callback);
-};
-
-//
-// ### function streamFrame (id, assoc, headers, callback)
-// #### @id {Number} stream id
-// #### @assoc {Number} associated stream id
-// #### @meta {Object} meta headers ( method, scheme, url, version )
-// #### @headers {Object} stream headers
-// #### @callback {Function} continuation callback
-// Create SYN_STREAM frame
-// (needed for server push and testing)
-//
-Framer.prototype.streamFrame = function streamFrame(id,
-                                                    assoc,
-                                                    meta,
-                                                    headers,
-                                                    callback) {
-  if (!this.version) {
-    return this.on('version', function() {
-      this.streamFrame(id, assoc, meta, headers, callback);
-    });
-  }
-
-  var self = this;
-  var dict = this.headersToDict(headers, function(headers) {
-    if (self.version === 2) {
-      if (meta.status)
-        headers.status = meta.status;
-      headers.version = meta.version || 'HTTP/1.1';
-      headers.url = meta.url;
-      if (meta.method)
-        headers.method = meta.method;
-    } else {
-      if (meta.status)
-        headers[':status'] = meta.status;
-      headers[':version'] = meta.version || 'HTTP/1.1';
-      headers[':path'] = meta.path || meta.url;
-      headers[':scheme'] = meta.scheme || 'https';
-      headers[':host'] = meta.host;
-      if (meta.method)
-        headers[':method'] = meta.method;
-    }
-  });
-
-  this._synFrame('SYN_STREAM', id, assoc, meta.priority, dict, callback);
-};
-
-//
-// ### function headersFrame (id, headers, callback)
-// #### @id {Number} Stream id
-// #### @headers {Object} Headers
-// #### @callback {Function}
-// Sends HEADERS frame
-//
-Framer.prototype.headersFrame = function headersFrame(id, headers, callback) {
-  if (!this.version) {
-    return this.on('version', function() {
-      this.headersFrame(id, headers, callback);
-    });
-  }
-
-  var self = this;
-  var dict = this.headersToDict(headers, function(headers) {});
-
-  this.deflate(dict, function (err, chunks, size) {
-    if (err)
-      return callback(err);
-
-    var offset = self.version === 2 ? 14 : 12,
-        total = offset - 8 + size,
-        frame = new Buffer(offset + size);
-
-    // Control + Version
-    frame.writeUInt16BE(0x8000 | self.version, 0, true);
-    // Type
-    frame.writeUInt16BE(8, 2, true);
-    // Length
-    frame.writeUInt32BE(total & 0x00ffffff, 4, true);
-    // Stream ID
-    frame.writeUInt32BE(id & 0x7fffffff, 8, true);
-
-    // Copy chunks
-    for (var i = 0; i < chunks.length; i++) {
-      chunks[i].copy(frame, offset);
-      offset += chunks[i].length;
-    }
-
-    callback(null, frame);
-  });
-};
-
-//
-// ### function dataFrame (id, fin, data, callback)
-// #### @id {Number} Stream id
-// #### @fin {Bool} Is this data frame last frame
-// #### @data {Buffer} Response data
-// #### @callback {Function}
-// Sends DATA frame
-//
-Framer.prototype.dataFrame = function dataFrame(id, fin, data, callback) {
-  if (!this.version) {
-    return this.on('version', function() {
-      this.dataFrame(id, fin, data, callback);
-    });
-  }
-
-  if (!fin && !data.length)
-    return callback(null, empty);
-
-  var frame = new Buffer(8 + data.length);
-
-  frame.writeUInt32BE(id & 0x7fffffff, 0, true);
-  frame.writeUInt32BE(data.length & 0x00ffffff, 4, true);
-  frame.writeUInt8(fin ? 0x01 : 0x0, 4, true);
-
-  if (data.length)
-    data.copy(frame, 8);
-
-  return callback(null, frame);
-};
-
-//
-// ### function pingFrame (id)
-// #### @id {Number} Ping ID
-// Sends PING frame
-//
-Framer.prototype.pingFrame = function pingFrame(id, callback) {
-  if (!this.version) {
-    return this.on('version', function() {
-      this.pingFrame(id, callback);
-    });
-  }
-
-  var header = new Buffer(12);
-
-  // Version and type
-  header.writeUInt32BE(0x80000006 | (this.version << 16), 0, true);
-  // Length
-  header.writeUInt32BE(0x00000004, 4, true);
-  // ID
-  header.writeUInt32BE(id, 8, true);
-
-  return callback(null, header);
-};
-
-//
-// ### function rstFrame (id, code, extra, callback)
-// #### @id {Number} Stream ID
-// #### @code {Number} RST Code
-// #### @extra {String} Extra debugging info
-// #### @callback {Function}
-// Sends PING frame
-//
-Framer.prototype.rstFrame = function rstFrame(id, code, extra, callback) {
-  if (!this.version) {
-    return this.on('version', function() {
-      this.rstFrame(id, code, extra, callback);
-    });
-  }
-
-  var header = new Buffer(16 +
-                          (this.debug ? Buffer.byteLength(extra || '') : 0));
-
-  // Version and type
-  header.writeUInt32BE(0x80000003 | (this.version << 16), 0, true);
-  // Length
-  header.writeUInt32BE(0x00000008, 4, true);
-  // Stream ID
-  header.writeUInt32BE(id & 0x7fffffff, 8, true);
-  // Status Code
-  header.writeUInt32BE(code, 12, true);
-
-  // Extra debugging information
-  if (this.debug && extra)
-    header.write(extra, 16);
-
-  return callback(null, header);
-};
-
-//
-// ### function settingsFrame (options, callback)
-// #### @options {Object} settings frame options
-// #### @callback {Function}
-// Sends SETTINGS frame with MAX_CONCURRENT_STREAMS and initial window
-//
-Framer.prototype.settingsFrame = function settingsFrame(options, callback) {
-  if (!this.version) {
-    return this.on('version', function() {
-      this.settingsFrame(options, callback);
-    });
-  }
-
-  var settings,
-      key = this.version === 2 ? '2/' + options.maxStreams :
-                                 '3/' + options.maxStreams + ':' +
-                                     options.windowSize;
-
-  if (!(settings = Framer.settingsCache[key])) {
-    var params = [];
-    if (isFinite(options.maxStreams)) {
-      params.push({
-        key: constants.settings.SETTINGS_MAX_CONCURRENT_STREAMS,
-        value: options.maxStreams
-      });
-    }
-    if (this.version > 2) {
-      params.push({
-        key: constants.settings.SETTINGS_INITIAL_WINDOW_SIZE,
-        value: options.windowSize
-      });
-    }
-
-    settings = new Buffer(12 + 8 * params.length);
-
-    // Version and type
-    settings.writeUInt32BE(0x80000004 | (this.version << 16), 0, true);
-    // Length
-    settings.writeUInt32BE((4 + 8 * params.length) & 0x00FFFFFF, 4, true);
-    // Count of entries
-    settings.writeUInt32BE(params.length, 8, true);
-
-    var offset = 12;
-    params.forEach(function(param) {
-      var flag = constants.settings.FLAG_SETTINGS_PERSIST_VALUE << 24;
-
-      if (this.version === 2)
-        settings.writeUInt32LE(flag | param.key, offset, true);
-      else
-        settings.writeUInt32BE(flag | param.key, offset, true);
-      offset += 4;
-      settings.writeUInt32BE(param.value & 0x7fffffff, offset, true);
-      offset += 4;
-    }, this);
-
-    Framer.settingsCache[key] = settings;
-  }
-
-  return callback(null, settings);
-};
-Framer.settingsCache = {};
-
-//
-// ### function windowUpdateFrame (id)
-// #### @id {Buffer} WindowUpdate ID
-// Sends WINDOW_UPDATE frame
-//
-Framer.prototype.windowUpdateFrame = function windowUpdateFrame(id, delta, cb) {
-  if (!this.version) {
-    return this.on('version', function() {
-      this.windowUpdateFrame(id, delta, cb);
-    });
-  }
-
-  var header = new Buffer(16);
-
-  // Version and type
-  header.writeUInt32BE(0x80000009 | (this.version << 16), 0, true);
-  // Length
-  header.writeUInt32BE(0x00000008, 4, true);
-  // ID
-  header.writeUInt32BE(id & 0x7fffffff, 8, true);
-  // Delta
-  if (delta > 0)
-    header.writeUInt32BE(delta & 0x7fffffff, 12, true);
-  else
-    header.writeUInt32BE(delta, 12, true);
-
-  return cb(null, header);
-};
-
-Framer.prototype.goawayFrame = function goawayFrame(lastId, status, cb) {
-  if (!this.version) {
-    return this.on('version', function() {
-      this.goawayFrame(lastId, status, cb);
-    });
-  }
-
-  var header = new Buffer(16);
-
-  // Version and type
-  header.writeUInt32BE(0x80000007 | (this.version << 16), 0, true);
-  // Length
-  header.writeUInt32BE(0x00000008, 4, true);
-  // Last-good-stream-ID
-  header.writeUInt32BE(lastId & 0x7fffffff, 8, true);
-  // Status
-  header.writeUInt32BE(status, 12, true);
-
-  return cb(null, header);
-};
deleted file mode 100644
--- a/testing/xpcshell/node-spdy/lib/spdy/protocol/index.js
+++ /dev/null
@@ -1,4 +0,0 @@
-exports.dictionary = require('./dictionary');
-exports.constants = require('./constants');
-exports.parser = require('./parser');
-exports.framer = require('./framer');
deleted file mode 100644
--- a/testing/xpcshell/node-spdy/lib/spdy/protocol/parser.js
+++ /dev/null
@@ -1,588 +0,0 @@
-var parser = exports;
-
-var spdy = require('../../spdy'),
-    utils = spdy.utils,
-    util = require('util'),
-    stream = require('stream'),
-    Buffer = require('buffer').Buffer;
-
-var legacy = !stream.Duplex;
-
-if (legacy) {
-  var DuplexStream = stream;
-} else {
-  var DuplexStream = stream.Duplex;
-}
-
-//
-// ### function Parser (connection)
-// #### @connection {spdy.Connection} connection
-// SPDY protocol frames parser's @constructor
-//
-function Parser(connection) {
-  DuplexStream.call(this);
-
-  this.paused = false;
-  this.buffer = [];
-  this.buffered = 0;
-  this.waiting = 8;
-
-  this.state = { type: 'frame-head' };
-  this.socket = connection.socket;
-  this.connection = connection;
-
-  this.version = null;
-  this.deflate = null;
-  this.inflate = null;
-
-  this.connection = connection;
-
-  if (legacy) {
-    this.readable = this.writable = true;
-  }
-}
-util.inherits(Parser, DuplexStream);
-
-//
-// ### function create (connection)
-// #### @connection {spdy.Connection} connection
-// @constructor wrapper
-//
-parser.create = function create(connection) {
-  return new Parser(connection);
-};
-
-//
-// ### function destroy ()
-// Just a stub.
-//
-Parser.prototype.destroy = function destroy() {
-};
-
-Parser.prototype._slice = function _slice(waiting) {
-  var buffer = new Buffer(waiting);
-  var sliced = 0;
-  var offset = 0;
-
-  while (waiting > offset && sliced < this.buffer.length) {
-    var chunk = this.buffer[sliced++],
-        overmatched = false;
-
-    // Copy chunk into `buffer`
-    if (chunk.length > waiting - offset) {
-      chunk.copy(buffer, offset, 0, waiting - offset);
-
-      this.buffer[--sliced] = chunk.slice(waiting - offset);
-      this.buffered += this.buffer[sliced].length;
-
-      overmatched = true;
-    } else {
-      chunk.copy(buffer, offset);
-    }
-
-    // Move offset and decrease amount of buffered data
-    offset += chunk.length;
-    this.buffered -= chunk.length;
-
-    if (overmatched) break;
-  }
-
-  // Remove used buffers
-  this.buffer = this.buffer.slice(sliced);
-
-  return buffer;
-};
-
-//
-// ### function _write (data, encoding, cb)
-// #### @data {Buffer} chunk of data
-// #### @encoding {Null} encoding
-// #### @cb {Function} callback
-// Writes or buffers data to parser
-//
-Parser.prototype._write = function write(data, encoding, cb) {
-  // Legacy compatibility
-  if (!cb) cb = function() {};
-
-  if (data !== undefined) {
-    // Buffer data
-    this.buffer.push(data);
-    this.buffered += data.length;
-  }
-
-  // Notify caller about state (for piping)
-  if (this.paused) {
-    this.needDrain = true;
-    cb();
-    return false;
-  }
-
-  if (this.needDrain) {
-    // Mark parser as drained
-    this.needDrain = false;
-    this.emit('drain');
-  }
-
-  // We shall not do anything until we get all expected data
-  if (this.buffered < this.waiting) {
-    // Emit DATA by chunks as they come
-    if (this.buffered !== 0 &&
-        this.state.header &&
-        !this.state.header.control) {
-      var buffer = this._slice(this.buffered);
-      this.waiting -= buffer.length;
-
-      this.emit('frame', {
-        type: 'DATA',
-        id: this.state.header.id,
-        fin: false,
-        compressed: (this.state.header.flags & 0x02) === 0x02,
-        data: buffer
-      });
-    }
-
-    cb();
-    return;
-  }
-
-  var self = this;
-  var buffer = this._slice(this.waiting);
-
-  // Executed parser for buffered data
-  this.paused = true;
-  var sync = true;
-  this.execute(this.state, buffer, function (err, waiting) {
-    // Propagate errors
-    if (err) {
-      // And unpause once execution finished
-      self.paused = false;
-
-      cb();
-      return self.emit('error', err);
-    }
-
-    // Set new `waiting`
-    self.waiting = waiting;
-
-    if (sync) {
-      utils.nextTick(function() {
-        // Unpause right before entering new `_write()` call
-        self.paused = false;
-        self._write(undefined, null, cb);
-      });
-    } else {
-      // Unpause right before entering new `_write()` call
-      self.paused = false;
-      self._write(undefined, null, cb);
-    }
-  });
-  sync = false;
-};
-
-if (legacy) {
-  //
-  // ### function write (data, encoding, cb)
-  // #### @data {Buffer} chunk of data
-  // #### @encoding {Null} encoding
-  // #### @cb {Function} callback
-  // Legacy method
-  //
-  Parser.prototype.write = Parser.prototype._write;
-
-  //
-  // ### function end ()
-  // Stream's end() implementation
-  //
-  Parser.prototype.end = function end() {
-    this.emit('end');
-  };
-}
-
-//
-// ### function setVersion (version)
-// #### @version {Number} Protocol version
-// Set protocol version to use
-//
-Parser.prototype.setVersion = function setVersion(version) {
-  this.version = version;
-  this.emit('version', version);
-  this.deflate = spdy.utils.zwrap(this.connection._spdyState.deflate);
-  this.inflate = spdy.utils.zwrap(this.connection._spdyState.inflate);
-};
-
-//
-// ### function execute (state, data, callback)
-// #### @state {Object} Parser's state
-// #### @data {Buffer} Incoming data
-// #### @callback {Function} continuation callback
-// Parse buffered data
-//
-Parser.prototype.execute = function execute(state, data, callback) {
-  if (state.type === 'frame-head') {
-    var header = state.header = this.parseHeader(data);
-
-    if (this.version === null && header.control) {
-      if (header.version !== 2 && header.version !== 3) {
-        return callback(new Error('Unsupported spdy version: ' +
-                                  header.version));
-      }
-      this.setVersion(header.version);
-    }
-
-    state.type = 'frame-body';
-    callback(null, header.length);
-  } else if (state.type === 'frame-body') {
-    var self = this;
-
-    // Data frame
-    if (!state.header.control) {
-      return onFrame(null, {
-        type: 'DATA',
-        id: state.header.id,
-        fin: (state.header.flags & 0x01) === 0x01,
-        compressed: (state.header.flags & 0x02) === 0x02,
-        data: data
-      });
-    } else {
-      // Control frame
-      this.parseBody(state.header, data, onFrame);
-    }
-
-    function onFrame(err, frame) {
-      if (err) return callback(err);
-
-      self.emit('frame', frame);
-
-      state.type = 'frame-head';
-      state.header = null;
-      callback(null, 8);
-    };
-  }
-};
-
-
-//
-// ### function parseHeader (data)
-// ### @data {Buffer} incoming data
-// Returns parsed SPDY frame header
-//
-Parser.prototype.parseHeader = function parseHeader(data) {
-  var header = {
-    control: (data.readUInt8(0) & 0x80) === 0x80 ? true : false,
-    version: null,
-    type: null,
-    id: null,
-    flags: data.readUInt8(4),
-    length: data.readUInt32BE(4) & 0x00ffffff
-  };
-
-  if (header.control) {
-    header.version = data.readUInt16BE(0) & 0x7fff;
-    header.type = data.readUInt16BE(2);
-  } else {
-    header.id = data.readUInt32BE(0) & 0x7fffffff;
-  }
-
-  return header;
-};
-
-
-//
-// ### function execute (header, body, callback)
-// #### @header {Object} Frame headers
-// #### @body {Buffer} Frame's body
-// #### @callback {Function} Continuation callback
-// Parse frame (decompress data and create streams)
-//
-Parser.prototype.parseBody = function parseBody(header, body, callback) {
-  // SYN_STREAM or SYN_REPLY
-  if (header.type === 0x01 || header.type === 0x02)
-    this.parseSynHead(header.type, header.flags, body, callback);
-  // RST_STREAM
-  else if (header.type === 0x03)
-    this.parseRst(body, callback);
-  // SETTINGS
-  else if (header.type === 0x04)
-    this.parseSettings(body, callback);
-  else if (header.type === 0x05)
-    callback(null, { type: 'NOOP' });
-  // PING
-  else if (header.type === 0x06)
-    this.parsePing(body, callback);
-  // GOAWAY
-  else if (header.type === 0x07)
-    this.parseGoaway(body, callback);
-  // HEADERS
-  else if (header.type === 0x08)
-    this.parseHeaders(body, callback);
-  // WINDOW_UPDATE
-  else if (header.type === 0x09)
-    this.parseWindowUpdate(body, callback);
-  // X-FORWARDED
-  else if (header.type === 0xf000)
-    this.parseXForwarded(body, callback);
-  else
-    callback(null, { type: 'unknown: ' + header.type, body: body });
-};
-
-
-//
-// ### function parseSynHead (type, flags, data)
-// #### @type {Number} Frame type
-// #### @flags {Number} Frame flags
-// #### @data {Buffer} input data
-// Returns parsed syn_* frame's head
-//
-Parser.prototype.parseSynHead = function parseSynHead(type,
-                                                      flags,
-                                                      data,
-                                                      callback) {
-  var stream = type === 0x01;
-  var offset = stream ? 10 : this.version === 2 ? 6 : 4;
-
-  if (data.length < offset)
-    return callback(new Error('SynHead OOB'));
-
-  var kvs = data.slice(offset);
-  this.parseKVs(kvs, function(err, headers) {
-    if (err)
-      return callback(err);
-
-    if (stream === 'SYN_STREAM' &&
-        (!headers.method || !(headers.path || headers.url))) {
-      return callback(new Error('Missing `:method` and/or `:path` header'));
-    }
-
-    callback(null, {
-      type: stream ? 'SYN_STREAM' : 'SYN_REPLY',
-      id: data.readUInt32BE(0, true) & 0x7fffffff,
-      associated: stream ? data.readUInt32BE(4, true) & 0x7fffffff : 0,
-      priority: stream ? data[8] >> 5 : 0,
-      fin: (flags & 0x01) === 0x01,
-      unidir: (flags & 0x02) === 0x02,
-      headers: headers,
-      url: headers.path || headers.url || ''
-    });
-  });
-};
-
-
-//
-// ### function parseHeaders (data, callback)
-// #### @data {Buffer} input data
-// #### @callback {Function} continuation
-// Parse HEADERS
-//
-Parser.prototype.parseHeaders = function parseHeaders(data, callback) {
-  var offset = this.version === 2 ? 6 : 4;
-  if (data.length < offset)
-    return callback(new Error('HEADERS OOB'));
-
-  var streamId = data.readUInt32BE(0, true) & 0x7fffffff;
-
-  this.parseKVs(data.slice(offset), function(err, headers) {
-    if (err)
-      return callback(err);
-
-    callback(null, {
-      type: 'HEADERS',
-      id: streamId,
-      headers: headers
-    });
-  });
-};
-
-
-//
-// ### function parseKVs (pairs, callback)
-// #### @pairs {Buffer} header pairs
-// #### @callback {Function} continuation
-// Returns hashmap of parsed headers
-//
-Parser.prototype.parseKVs = function parseKVs(pairs, callback) {
-  var self = this;
-  this.inflate(pairs, function(err, chunks, length) {
-    if (err)
-      return callback(err);
-
-    var pairs = Buffer.concat(chunks, length);
-
-    var size = self.version === 2 ? 2 : 4;
-    if (pairs.length < size)
-      return callback(new Error('KV OOB'));
-
-    var count = size === 2 ? pairs.readUInt16BE(0, true) :
-                             pairs.readUInt32BE(0, true),
-        headers = {};
-
-    pairs = pairs.slice(size);
-
-    function readString() {
-      if (pairs.length < size)
-        return null;
-      var len = size === 2 ? pairs.readUInt16BE(0, true) :
-                             pairs.readUInt32BE(0, true);
-
-      if (pairs.length < size + len) {
-        return null;
-      }
-      var value = pairs.slice(size, size + len);
-
-      pairs = pairs.slice(size + len);
-
-      return value.toString();
-    }
-
-    while(count > 0) {
-      var key = readString(),
-          value = readString();
-
-      if (key === null || value === null)
-        return callback(new Error('Headers OOB'));
-
-      if (self.version >= 3)
-        headers[key.replace(/^:/, '')] = value;
-      else
-        headers[key] = value;
-      count--;
-    }
-
-    callback(null, headers);
-  });
-};
-
-
-//
-// ### function parseRst (data, callback)
-// #### @data {Buffer} input data
-// #### @callback {Function} continuation
-// Parse RST
-//
-Parser.prototype.parseRst = function parseRst(data, callback) {
-  if (data.length < 8)
-    return callback(new Error('RST OOB'));
-
-  callback(null, {
-    type: 'RST_STREAM',
-    id: data.readUInt32BE(0, true) & 0x7fffffff,
-    status: data.readUInt32BE(4, true),
-    extra: data.length > 8 ? data.slice(8) : null
-  });
-};
-
-
-//
-// ### function parseSettings (data, callback)
-// #### @data {Buffer} input data
-// #### @callback {Function} continuation
-// Parse SETTINGS
-//
-Parser.prototype.parseSettings = function parseSettings(data, callback) {
-  if (data.length < 4)
-    return callback(new Error('SETTINGS OOB'));
-
-  var settings = {},
-      number = data.readUInt32BE(0, true),
-      idMap = {
-        1: 'upload_bandwidth',
-        2: 'download_bandwidth',
-        3: 'round_trip_time',
-        4: 'max_concurrent_streams',
-        5: 'current_cwnd',
-        6: 'download_retrans_rate',
-        7: 'initial_window_size',
-        8: 'client_certificate_vector_size'
-      };
-
-  if (data.length < 4 + number * 8)
-    return callback(new Error('SETTINGS OOB#2'));
-
-  for (var i = 0; i < number; i++) {
-    var id = (this.version === 2 ? data.readUInt32LE(4 + i * 8, true) :
-                                   data.readUInt32BE(4 + i * 8, true)),
-        flags = (id >> 24) & 0xff;
-    id = id & 0xffffff;
-
-    var name = idMap[id];
-
-    settings[id] = settings[name] = {
-      persist: !!(flags & 0x1),
-      persisted: !!(flags & 0x2),
-      value: data.readUInt32BE(8 + (i*8), true)
-    };
-  }
-
-  callback(null, {
-    type: 'SETTINGS',
-    settings: settings
-  });
-};
-
-
-//
-// ### function parseGoaway (data, callback)
-// #### @data {Buffer} input data
-// #### @callback {Function} continuation
-// Parse PING
-//
-Parser.prototype.parsePing = function parsePing(body, callback) {
-  if (body.length < 4)
-    return callback(new Error('PING OOB'));
-  callback(null, { type: 'PING', pingId: body.readUInt32BE(0, true) });
-};
-
-
-//
-// ### function parseGoaway (data, callback)
-// #### @data {Buffer} input data
-// #### @callback {Function} continuation
-// Parse GOAWAY
-//
-Parser.prototype.parseGoaway = function parseGoaway(data, callback) {
-  if (data.length < 4)
-    return callback(new Error('GOAWAY OOB'));
-
-  callback(null, {
-    type: 'GOAWAY',
-    lastId: data.readUInt32BE(0, true) & 0x7fffffff
-  });
-};
-
-
-//
-// ### function parseWindowUpdate (data, callback)
-// #### @data {Buffer} input data
-// #### @callback {Function} continuation
-// Parse WINDOW_UPDATE
-//
-Parser.prototype.parseWindowUpdate = function parseWindowUpdate(data, callback) {
-  if (data.length < 8)
-    return callback(new Error('WINDOW_UPDATE OOB'));
-
-  callback(null, {
-    type: 'WINDOW_UPDATE',
-    id: data.readUInt32BE(0, true) & 0x7fffffff,
-    delta: data.readUInt32BE(4, true) & 0x7fffffff
-  });
-};
-
-
-//
-// ### function parseXForwarded (data, callback)
-// #### @data {Buffer} input data
-// #### @callback {Function} continuation
-// Parse X_FORWARDED
-//
-Parser.prototype.parseXForwarded = function parseXForwarded(data, callback) {
-  if (data.length < 4)
-    return callback(new Error('X_FORWARDED OOB'));
-
-  var len = data.readUInt32BE(0, true);
-  if (len + 4 > data.length)
-    return callback(new Error('X_FORWARDED host length OOB'));
-
-  callback(null, {
-    type: 'X_FORWARDED',
-    host: data.slice(4, 4 + len).toString()
-  });
-};
deleted file mode 100644
--- a/testing/xpcshell/node-spdy/lib/spdy/response.js
+++ /dev/null
@@ -1,208 +0,0 @@
-var spdy = require('../spdy'),
-    utils = spdy.utils,
-    http = require('http'),
-    Stream = require('stream').Stream,
-    res = http.ServerResponse.prototype;
-
-//
-// ### function _renderHeaders ()
-// Copy pasted from lib/http.js
-// (added lowercase)
-//
-exports._renderHeaders = function renderHeaders() {
-  if (this._header)
-    throw new Error("Can't render headers after they are sent to the client.");
-
-  var keys = Object.keys(this._headerNames);
-  for (var i = 0, l = keys.length; i < l; i++) {
-    var key = keys[i];
-    this._headerNames[key] = this._headerNames[key].toLowerCase();
-  }
-
-  return res._renderHeaders.call(this);
-};
-
-//
-// ### function writeHead (statusCode)
-// #### @statusCode {Number} HTTP Status code
-// .writeHead() wrapper
-// (Sorry, copy pasted from lib/http.js)
-//
-exports.writeHead = function writeHead(statusCode) {
-  if (this._headerSent)
-    return;
-  this._headerSent = true;
-
-  var reasonPhrase, headers = {}, headerIndex;
-
-  if (typeof arguments[1] == 'string') {
-    reasonPhrase = arguments[1];
-    headerIndex = 2;
-  } else {
-    reasonPhrase = http.STATUS_CODES[statusCode] || 'unknown';
-    headerIndex = 1;
-  }
-  this.statusCode = statusCode;
-
-  var obj = arguments[headerIndex];
-
-  if (obj && this._headers) {
-    // Slow-case: when progressive API and header fields are passed.
-    headers = this._renderHeaders();
-
-    // handle object case
-    var keys = Object.keys(obj);
-    for (var i = 0; i < keys.length; i++) {
-      var k = keys[i];
-      if (k)
-        headers[k] = obj[k];
-    }
-  } else if (this._headers) {
-    // only progressive api is used
-    headers = this._renderHeaders();
-  } else {
-    // only writeHead() called
-    headers = obj;
-  }
-
-  // cleanup
-  this._header = '';
-
-  // Do not send data to new connections after GOAWAY
-  if (this.socket._isGoaway())
-    return;
-
-  // Date header
-  if (this.sendDate === true) {
-    if (headers === undefined)
-      headers = {};
-    if (headers.date === undefined)
-      headers.date = new Date().toUTCString();
-  }
-
-  this.socket._lock(function() {
-    var socket = this;
-
-    this._spdyState.framer.replyFrame(
-      this._spdyState.id,
-      statusCode,
-      reasonPhrase,
-      headers,
-      function (err, frame) {
-        if (err) {
-          socket._unlock();
-          socket.emit('error', err);
-          return;
-        }
-
-        socket.connection.cork();
-        socket.connection.write(frame);
-        utils.nextTick(function() {
-          socket.connection.uncork();
-        });
-        socket._unlock();
-      }
-    );
-  });
-};
-
-//
-// ### function end (data, encoding, cb)
-// #### @data {Buffer|String} (optional) data
-// #### @encoding {String} (optional) string encoding
-// #### @cb {Function}
-// Send final data
-//
-exports.end = function end(data, encoding, cb) {
-  if (this.socket)
-    this.socket._spdyState.ending = true;
-
-  this.constructor.prototype.end.call(this, data, encoding, cb);
-};
-
-//
-// ### function push (url, headers, callback)
-// #### @url {String} absolute or relative url (from root anyway)
-// #### @headers {Object} response headers
-// #### @callbacks {Function} continuation that will receive stream object
-// Initiates push stream
-//
-exports.push = function push(url, headers, priority, callback) {
-  var socket = this.socket;
-
-  if (!callback && typeof priority === 'function') {
-    callback = priority;
-    priority = null;
-  }
-  if (!priority && typeof priority !== 'number')
-    priority = 7;
-
-  if (!callback)
-    callback = function() {};
-
-  if (!socket || socket._destroyed) {
-    var stub = new Stream();
-    var err = Error('Can\'t open push stream, parent socket destroyed');
-    utils.nextTick(function() {
-      if (stub.listeners('error').length !== 0)
-        stub.emit('error', err);
-      callback(err);
-    });
-    return stub;
-  }
-
-  var id = socket.connection._spdyState.pushId += 2,
-      scheme = socket._spdyState.scheme,
-      host = headers.host || socket._spdyState.host || 'localhost',
-      fullUrl = /^\//.test(url) ? scheme + '://' + host + url : url;
-
-  var stream = new spdy.Stream(socket.connection, {
-    type: 'SYN_STREAM',
-    id: id,
-    associated: socket._spdyState.id,
-    priority: priority,
-    headers: {}
-  });
-
-  stream.associated = socket;
-
-  socket._lock(function() {
-    this._spdyState.framer.streamFrame(
-      id,
-      this._spdyState.id,
-      {
-        method: 'GET',
-        path: url,
-        url: fullUrl,
-        scheme: scheme,
-        host: host,
-        version: 'HTTP/1.1',
-        priority: priority,
-        status: 200
-      },
-      headers,
-      function(err, frame) {
-        if (err) {
-          socket._unlock();
-          if (callback)
-            callback(err);
-          stream.destroy(err);
-          return;
-        } else {
-          socket.connection.cork();
-          socket.connection.write(frame);
-          utils.nextTick(function() {
-            socket.connection.uncork();
-          });
-          socket._unlock();
-        }
-
-        stream.emit('acknowledge');
-        if (callback)
-          callback(null, stream);
-      }
-    );
-  });
-
-  return stream;
-};
deleted file mode 100644
--- a/testing/xpcshell/node-spdy/lib/spdy/scheduler.js
+++ /dev/null
@@ -1,101 +0,0 @@
-var spdy = require('../spdy');
-var utils = spdy.utils;
-var scheduler = exports;
-
-//
-// ### function Scheduler (connection)
-// #### @connection {spdy.Connection} active connection
-// Connection's streams scheduler
-//
-function Scheduler(connection) {
-  this.connection = connection;
-  this.priorities = [[], [], [], [], [], [], [], []];
-  this._tickListener = this._tickListener.bind(this);
-  this._tickListening = false;
-  this._tickCallbacks = [];
-  this._corked = false;
-}
-
-//
-// ### function create (connection)
-// #### @connection {spdy.Connection} active connection
-//
-exports.create = function create(connection) {
-  return new Scheduler(connection);
-};
-
-//
-// ### function schedule (stream, data)
-// #### @stream {spdy.Stream} Source stream
-// #### @data {Buffer} data to write on tick
-// Use stream priority to invoke callbacks in right order
-//
-Scheduler.prototype.schedule = function schedule(stream, data) {
-  // Ignore data from destroyed stream
-  if (stream._spdyState.destroyed)
-    return;
-  this.scheduleLast(stream, data);
-};
-
-//
-// ### function scheduleLast (stream, data)
-// #### @stream {spdy.Stream} Source stream
-// #### @data {Buffer} data to write on tick
-// Use stream priority to invoke callbacks in right order
-//
-Scheduler.prototype.scheduleLast = function scheduleLast(stream, data) {
-  var priority = stream._spdyState.priority;
-  priority = Math.min(priority, 7);
-  priority = Math.max(priority, 0);
-  this.priorities[priority].push(data);
-};
-
-//
-// ### function tickListener ()
-//
-Scheduler.prototype._tickListener = function tickListener() {
-  var priorities = this.priorities;
-  var tickCallbacks = this._tickCallbacks;
-
-  this._tickListening = false;
-  this.priorities = [[], [], [], [], [], [], [], []];
-  this._tickCallbacks = [];
-
-  // Run all priorities
-  for (var i = 0; i < 8; i++)
-    for (var j = 0; j < priorities[i].length; j++)
-      this.connection.write(priorities[i][j]);
-
-  // Invoke callbacks
-  for (var i = 0; i < tickCallbacks.length; i++)
-    tickCallbacks[i]();
-  if (this._corked) {
-    this.connection.uncork();
-    if (this._tickListening)
-      this.connection.cork();
-    else
-      this._corked = false;
-  }
-};
-
-//
-// ### function tick ()
-// Add .nextTick callback if not already present
-//
-Scheduler.prototype.tick = function tick(cb) {
-  if (cb)
-    this._tickCallbacks.push(cb);
-  if (this._tickListening)
-    return;
-  this._tickListening = true;
-
-  if (!this._corked) {
-    this.connection.cork();
-    this._corked = true;
-  }
-  if (!this.connection._spdyState.parser.needDrain) {
-    utils.nextTick(this._tickListener);
-  } else {
-    this.connection._spdyState.parser.once('drain', this._tickListener);
-  }
-};
deleted file mode 100644
--- a/testing/xpcshell/node-spdy/lib/spdy/server.js
+++ /dev/null
@@ -1,329 +0,0 @@
-var spdy = require('../spdy'),
-    util = require('util'),
-    https = require('https');
-
-var Connection = spdy.Connection;
-
-//
-// ### function instantiate (HTTPSServer)
-// #### @HTTPSServer {https.Server|Function} Base server class
-// Will return constructor for SPDY Server, based on the HTTPSServer class
-//
-function instantiate(HTTPSServer) {
-  //
-  // ### function Server (options, requestListener)
-  // #### @options {Object} tls server options
-  // #### @requestListener {Function} (optional) request callback
-  // SPDY Server @constructor
-  //
-  function Server(options, requestListener) {
-    // Initialize
-    this._init(HTTPSServer, options, requestListener);
-
-    // Wrap connection handler
-    this._wrap();
-  };
-  util.inherits(Server, HTTPSServer);
-
-  // Copy prototype methods
-  Object.keys(proto).forEach(function(key) {
-    this[key] = proto[key];
-  }, Server.prototype);
-
-  return Server;
-}
-exports.instantiate = instantiate;
-
-// Common prototype for all servers
-var proto = {};
-
-//
-// ### function _init(base, options, listener)
-// #### @base {Function} (optional) base server class (https.Server)
-// #### @options {Object} tls server options
-// #### @handler {Function} (optional) request handler
-// Initializer.
-//
-proto._init = function _init(base, options, handler) {
-  var state = {};
-  this._spdyState = state;
-
-  if (!options)
-    options = {};
-
-  // Copy user supplied options
-  options = util._extend({}, options);
-
-  var supportedProtocols = [
-    'spdy/3.1', 'spdy/3', 'spdy/2',
-    'http/1.1', 'http/1.0'
-  ];
-  options.NPNProtocols = supportedProtocols;
-  options.ALPNProtocols = supportedProtocols;
-  options.isServer = true;
-
-  // Header compression is enabled by default in servers, in contrast to clients
-  // where it is disabled to prevent CRIME attacks.
-  // See: https://groups.google.com/d/msg/spdy-dev/6mVYRv-lbuc/qGcW2ldOpt8J
-  if (options.headerCompression !== false)
-    options.headerCompression = true;
-
-  state.options = options;
-  state.reqHandler = handler;
-
-  if (options.plain && !options.ssl)
-    base.call(this, handler);
-  else
-    base.call(this, options, handler);
-
-  // Use https if neither NPN or ALPN is supported
-  if (!process.features.tls_npn && !process.features.tls_alpn &&
-      !options.debug && !options.plain)
-    return;
-};
-
-//
-// ### function _wrap()
-// Wrap connection handler and add logic.
-//
-proto._wrap = function _wrap() {
-  var self = this,
-      state = this._spdyState;
-
-  // Wrap connection handler
-  var event = state.options.plain && !state.options.ssl ? 'connection' :
-                                                          'secureConnection',
-      handler = this.listeners(event)[0];
-
-  state.handler = handler;
-
-  this.removeAllListeners(event);
-
-  // 2 minutes default timeout
-  if (state.options.timeout !== undefined)
-    this.timeout = state.options.timeout;
-  else
-    this.timeout = this.timeout || 2 * 60 * 1000;
-
-  // Normal mode, use NPN or ALPN to fallback to HTTPS
-  if (!state.options.plain)
-    return this.on(event, this._onConnection.bind(this));
-
-  // In case of plain connection, we must fallback to HTTPS if first byte
-  // is not equal to 0x80.
-  this.on(event, function(socket) {
-    var history = [],
-        _emit = socket.emit;
-
-    // Add 'data' listener, otherwise 'data' events won't be emitted
-    if (spdy.utils.isLegacy) {
-      function ondata() {};
-      socket.once('data', ondata);
-    }
-
-    // 2 minutes timeout, as http.js does by default
-    socket.setTimeout(self.timeout);
-
-    socket.emit = function emit(event, data) {
-      history.push(Array.prototype.slice.call(arguments));
-
-      if (event === 'data') {
-        // Legacy
-        if (spdy.utils.isLegacy)
-          onFirstByte.call(socket, data);
-      } else if (event === 'readable') {
-        // Streams
-        onReadable.call(socket);
-      } else if (event === 'end' ||
-                 event === 'close' ||
-                 event === 'error' ||
-                 event === 'timeout') {
-        // We shouldn't get there if any data was received
-        fail();
-      }
-    };
-
-    function fail() {
-      socket.emit = _emit;
-      history = null;
-      socket.removeListener('readable', onReadable);
-
-      try {
-        socket.destroy();
-      } catch (e) {
-      }
-    }
-
-    function restore() {
-      var copy = history.slice();
-      history = null;
-
-      socket.removeListener('readable', onReadable);
-      if (spdy.utils.isLegacy)
-        socket.removeListener('data', ondata);
-      socket.emit = _emit;
-      for (var i = 0; i < copy.length; i++) {
-        if (copy[i][0] !== 'data' || spdy.utils.isLegacy)
-          socket.emit.apply(socket, copy[i]);
-        if (copy[i][0] === 'end' && socket.onend)
-          socket.onend();
-      }
-    }
-
-    function onFirstByte(data) {
-      // Ignore empty packets
-      if (data.length === 0)
-        return;
-
-      if (data[0] === 0x80)
-        self._onConnection(socket);
-      else
-        handler.call(self, socket);
-
-      // Fire events
-      restore();
-
-      // NOTE: If we came there - .ondata() will be called anyway in this tick,
-      // so there're no need to call it manually
-    };
-
-    // Hack to make streams2 work properly
-    if (!spdy.utils.isLegacy)
-      socket.on('readable', onReadable);
-
-    function onReadable() {
-      var data = socket.read(1);
-
-      // Ignore empty packets
-      if (!data)
-        return;
-      socket.removeListener('readable', onReadable);
-
-      // `.unshift()` emits `readable` event. Thus `emit` method should
-      // be restored before calling it.
-      socket.emit = _emit;
-
-      // Put packet back where it was before
-      socket.unshift(data);
-
-      if (data[0] === 0x80)
-        self._onConnection(socket);
-      else
-        handler.call(self, socket);
-
-      // Fire events
-      restore();
-
-      if (socket.ondata) {
-        data = socket.read(socket._readableState.length);
-        if (data)
-          socket.ondata(data, 0, data.length);
-      }
-    }
-  });
-};
-
-//
-// ### function _onConnection (socket)
-// #### @socket {Stream} incoming socket
-// Server's connection handler wrapper.
-//
-proto._onConnection = function _onConnection(socket) {
-  var self = this,
-      state = this._spdyState;
-
-  // Fallback to HTTPS if needed
-  var selectedProtocol = socket.npnProtocol || socket.alpnProtocol;
-  if ((!selectedProtocol || !selectedProtocol.match(/spdy/)) &&
-      !state.options.debug && !state.options.plain) {
-    return state.handler.call(this, socket);
-  }
-
-  // Wrap incoming socket into abstract class
-  var connection = new Connection(socket, state.options, this);
-  if (selectedProtocol === 'spdy/3.1')
-    connection._setVersion(3.1);
-  else if (selectedProtocol === 'spdy/3')
-    connection._setVersion(3);
-  else if (selectedProtocol === 'spdy/2')
-    connection._setVersion(2);
-
-  // Emulate each stream like connection
-  connection.on('stream', state.handler);
-
-  connection.on('connect', function onconnect(req, socket) {
-    socket.streamID = req.streamID = req.socket._spdyState.id;
-    socket.isSpdy = req.isSpdy = true;
-    socket.spdyVersion = req.spdyVersion = req.socket._spdyState.framer.version;
-
-    socket.once('finish', function onfinish() {
-      req.connection.end();
-    });
-
-    self.emit('connect', req, socket);
-  });
-
-  connection.on('request', function onrequest(req, res) {
-    // Copy extension methods
-    res._renderHeaders = spdy.response._renderHeaders;
-    res.writeHead = spdy.response.writeHead;
-    res.end = spdy.response.end;
-    res.push = spdy.response.push;
-    res.streamID = req.streamID = req.socket._spdyState.id;
-    res.spdyVersion = req.spdyVersion = req.socket._spdyState.framer.version;
-    res.isSpdy = req.isSpdy = true;
-    res.addTrailers = function addTrailers(headers) {
-      res.socket.sendHeaders(headers);
-    };
-
-    // Make sure that keep-alive won't apply to the response
-    res._last = true;
-
-    // Chunked encoding is not supported in SPDY
-    res.useChunkedEncodingByDefault = false;
-
-    // Populate trailing headers
-    req.connection.on('headers', function(headers) {
-      Object.keys(headers).forEach(function(key) {
-        req.trailers[key] = headers[key];
-      });
-      req.emit('trailers', headers);
-    });
-
-    self.emit('request', req, res);
-  });
-
-  connection.on('error', function onerror(e) {
-    socket.destroy(e.errno === 'EPIPE' ? undefined : e);
-  });
-};
-
-// Export Server instantiated from https.Server
-var Server = instantiate(https.Server);
-exports.Server = Server;
-
-//
-// ### function create (base, options, requestListener)
-// #### @base {Function} (optional) base server class (https.Server)
-// #### @options {Object} tls server options
-// #### @requestListener {Function} (optional) request callback
-// @constructor wrapper
-//
-exports.create = function create(base, options, requestListener) {
-  var server;
-  if (typeof base === 'function') {
-    server = instantiate(base);
-  } else {
-    server = Server;
-
-    requestListener = options;
-    options = base;
-    base = null;
-  }
-
-  // Instantiate http server if `ssl: false`
-  if (!base && options && options.plain && options.ssl === false)
-    return exports.create(require('http').Server, options, requestListener);
-
-  return new server(options, requestListener);
-};
deleted file mode 100644
--- a/testing/xpcshell/node-spdy/lib/spdy/stream.js
+++ /dev/null
@@ -1,1180 +0,0 @@
-var spdy = require('../spdy');
-var zlib = require('zlib');
-var utils = spdy.utils;
-var assert = require('assert');
-var util = require('util');
-var stream = require('stream');
-var Buffer = require('buffer').Buffer;
-var constants = spdy.protocol.constants;
-
-var empty = new Buffer(0);
-
-if (!/^v(0\.10|0\.8|0\.9)\./.test(process.version))
-  var httpCommon = require('_http_common');
-
-
-//
-// ### function Stream (connection, options)
-// #### @connection {Connection} SPDY Connection
-// #### @options {Object} Stream options
-// Abstract stream @constructor
-//
-function Stream(connection, options) {
-  var self = this;
-
-  utils.DuplexStream.call(this);
-
-  this.connection = connection;
-  this.socket = connection.socket;
-  this.encrypted = connection.encrypted;
-  this.associated = null;
-
-  // 0.10 hack
-  this._handle = {
-    readStop: function() { self._readStop() },
-    readStart: function() { self._readStart() }
-  };
-
-  var state = {};
-  this._spdyState = state;
-  state.timeout = connection.timeout;
-  state.timeoutTimer = null;
-  state.framer = connection._spdyState.framer;
-  state.initialized = false;
-  state.ending = false;
-  state.ended = false;
-  state.paused = false;
-  state.finishAttached = false;
-  state.decompress = options.decompress;
-  state.decompressor = null;
-
-  // Store id
-  state.id = options.id;
-  state.associated = options.associated;
-  state.headers = options.headers || {};
-
-  // Protocol standard compliance:
-  // Client does not have to send this header, we must assume,
-  // that it can handle compression
-  if (connection._spdyState.isServer && !state.associated &&
-      !state.headers['accept-encoding']) {
-    state.headers['accept-encoding'] = 'gzip, deflate';
-  }
-
-  if (connection._spdyState.xForward !== null)
-    state.headers['x-forwarded-for'] = connection._spdyState.xForward;
-
-  // Increment counters
-  state.isPush = !connection._spdyState.isServer && state.associated;
-  connection._spdyState.counters.streamCount++;
-  if (state.isPush)
-    connection._spdyState.counters.pushCount++;
-  connection._addStream(this);
-
-  // Useful for PUSH streams
-  state.scheme = state.headers.scheme;
-  state.host = state.headers.host;
-
-  if (state.isPush && state.headers['content-encoding']) {
-    var compression = state.headers['content-encoding'];
-
-    // If compression was requested - setup decompressor
-    if (compression === 'gzip' || compression === 'deflate')
-      this._setupDecompressor(compression);
-  }
-
-  // True if inside chunked write
-  state.chunkedWrite = false;
-
-  // Store options
-  state.options = options;
-  state.isClient = !!options.client;
-  state.parseRequest = !!options.client;
-
-  // RST_STREAM code if any
-  state.rstCode = constants.rst.PROTOCOL_ERROR;
-  state.destroyed = false;
-
-  state.closedBy = {
-    them: false,
-    us: false
-  };
-
-  // Store priority
-  state.priority = options.priority;
-
-  // How much data can be sent TO client before next WINDOW_UPDATE
-  state.sinkSize = connection._spdyState.initialSinkSize;
-  state.initialSinkSize = state.sinkSize;
-
-  // When data needs to be send, but window is too small for it - it'll be
-  // queued in this buffer
-  state.sinkBuffer = [];
-  state.sinkDraining = false;
-
-  // How much data can be sent BY client before next WINDOW_UPDATE
-  state.windowSize = connection._spdyState.initialWindowSize;
-  state.initialWindowSize = state.windowSize;
-
-  this._init();
-};
-util.inherits(Stream, utils.DuplexStream);
-exports.Stream = Stream;
-
-// Parser lookup methods
-Stream.prototype._parserHeadersComplete = function parserHeadersComplete() {
-  var method;
-  if (this.parser)
-    method = this.parser.onHeadersComplete || this.parser[1];
-  if (!method || !utils.isArgvParser)
-    return method;
-
-  return function onHeadersCompleteWrap(info) {
-    // NOTE: shouldKeepAlive = false
-    return method.call(this,
-                       info.versionMajor,
-                       info.versionMinor,
-                       info.headers,
-                       info.method,
-                       info.url,
-                       info.statusCode,
-                       info.statusMessage,
-                       info.upgrade,
-                       false);
-  };
-};
-
-Stream.prototype._parserBody = function parserBody() {
-  if (this.parser)
-    return this.parser.onBody || this.parser[2];
-};
-
-Stream.prototype._parserMessageComplete = function parserMessageComplete() {
-  if (this.parser)
-    return this.parser.onMessageComplete || this.parser[3];
-};
-
-//
-// ### function init ()
-// Initialize stream
-//
-Stream.prototype._init = function init() {
-  var state = this._spdyState;
-
-  this.setTimeout();
-  this.ondata = this.onend = null;
-
-  if (utils.isLegacy)
-    this.readable = this.writable = true;
-
-  // Call .onend()
-  this.once('end', function() {
-    var self = this;
-    utils.nextTick(function() {
-      var onHeadersComplete = self._parserHeadersComplete();
-      if (!onHeadersComplete && self.onend)
-        self.onend();
-    });
-  });
-
-  // Handle half-close
-  this.once('finish', function onfinish() {
-    if (state.chunkedWrite)
-      return this.once('_chunkDone', onfinish);
-
-    var self = this;
-    this._writeData(true, empty, function() {
-      state.closedBy.us = true;
-      if (state.sinkBuffer.length !== 0)
-        return;
-      if (utils.isLegacy)
-        self.emit('full-finish');
-      self._handleClose();
-    });
-  });
-
-  if (state.isClient) {
-    var httpMessage;
-    Object.defineProperty(this, '_httpMessage', {
-      set: function(val) {
-        if (val)
-          this._attachToRequest(val);
-        httpMessage = val;
-      },
-      get: function() {
-        return httpMessage;
-      },
-      configurable: true,
-      enumerable: true
-    });
-  }
-};
-
-Stream.prototype._readStop = function readStop() {
-  this._spdyState.paused = true;
-};
-
-Stream.prototype._readStart = function readStart() {
-  this._spdyState.paused = false;
-
-  // Send window update if needed
-  this._read();
-};
-
-if (utils.isLegacy) {
-  Stream.prototype.pause = function pause() {
-    this._readStop();
-  };
-  Stream.prototype.resume = function resume() {
-    this._readStart();
-  };
-}
-
-//
-// ### function _isGoaway ()
-// Returns true if any writes to that stream should be ignored
-//
-Stream.prototype._isGoaway = function _isGoaway() {
-  return this.connection._spdyState.goaway &&
-         this._spdyState.id > this.connection._spdyState.goaway;
-};
-
-//
-// ### function start (url, headers)
-// #### @url {String}
-// #### @headers {Object}
-// Start stream, internal
-//
-Stream.prototype._start = function start(url, headers) {
-  var state = this._spdyState;
-  var headerList = [];
-
-  // Create list of headeres
-  Object.keys(headers).map(function(key) {
-    if (key !== 'method' &&
-        key !== 'url' &&
-        key !== 'version' &&
-        key !== 'scheme' &&
-        key !== 'status' &&
-        key !== 'path') {
-      headerList.push(key, headers[key]);
-    }
-  });
-
-  var info = {
-    url: url,
-    headers: headerList,
-    versionMajor: 1,
-    versionMinor: 1,
-    method: httpCommon ? httpCommon.methods.indexOf(headers.method) :
-                         headers.method,
-    statusCode: false,
-    upgrade: headers.method === 'CONNECT'
-  };
-
-  // Write data directly to the parser callbacks
-  var onHeadersComplete = this._parserHeadersComplete();
-  if (onHeadersComplete) {
-    onHeadersComplete.call(this.parser, info);
-
-    // onHeadersComplete doesn't handle CONNECT
-    if (headers.method === 'CONNECT') {
-      // We don't need to handle a lack of listeners here, since there
-      //   should always be a listener in server.js
-      var req = this.parser.incoming;
-      if (this.listeners('data').length) {
-        // 0.11+ only (assuming nobody other than the http lib has attached)
-        this.removeAllListeners('data');
-        this.skipBodyParsing = true;
-      }
-      this.connection.emit('connect', req, req.socket);
-    }
-  } else {
-    this.emit('headersComplete', info);
-  }
-
-  state.initialized = true;
-};
-
-//
-// ### function attachToRequest (req)
-// #### @req {ClientRequest}
-// Attach to node.js' response
-//
-Stream.prototype._attachToRequest = function attachToRequest(res) {
-  var self = this;
-
-  res.addTrailers = function addTrailers(headers) {
-    self.sendHeaders(headers);
-  };
-
-  this.on('headers', function(headers) {
-    var req = res.parser.incoming;
-    if (req) {
-      Object.keys(headers).forEach(function(key) {
-        req.trailers[key] = headers[key];
-      });
-      req.emit('trailers', headers);
-    }
-  });
-};
-
-//
-// ### function sendHeaders (headers)
-// #### @headers {Object}
-//
-Stream.prototype.sendHeaders = function sendHeaders(headers) {
-  var self = this;
-  var state = this._spdyState;
-
-  // Reset timeout
-  this.setTimeout();
-
-  var connection = this.connection;
-  this._lock(function() {
-    state.framer.headersFrame(state.id, headers, function(err, frame) {
-      if (err) {
-        self._unlock();
-        return self.emit('error', err);
-      }
-
-      connection.write(frame);
-      self._unlock();
-    });
-  });
-};
-
-//
-// ### function setTimeout (timeout, callback)
-// #### @timeout {Number}
-// #### @callback {Function}
-//
-Stream.prototype.setTimeout = function _setTimeout(timeout, callback) {
-  var self = this;
-  var state = this._spdyState;
-
-  if (callback)
-    this.once('timeout', callback);
-
-  // Keep PUSH's parent alive
-  if (this.associated)
-    this.associated.setTimeout();
-
-  state.timeout = timeout !== undefined ? timeout : state.timeout;
-
-  if (state.timeoutTimer) {
-    clearTimeout(state.timeoutTimer);
-    state.timeoutTimer = null;
-  }
-
-  if (!state.timeout)
-    return;
-
-  state.timeoutTimer = setTimeout(function() {
-    self.emit('timeout');
-  }, state.timeout);
-};
-
-//
-// ### function _handleClose ()
-// Close stream if it was closed by both server and client
-//
-Stream.prototype._handleClose = function _handleClose() {
-  var state = this._spdyState;
-  if (state.closedBy.them && state.closedBy.us)
-    this.close();
-};
-
-//
-// ### function close ()
-// Destroys stream
-//
-Stream.prototype.close = function close() {
-  this.destroy();
-};
-
-//
-// ### function destroy (error)
-// #### @error {Error} (optional) error
-// Destroys stream
-//
-Stream.prototype.destroy = function destroy(error) {
-  var state = this._spdyState;
-  if (state.destroyed)
-    return;
-  state.destroyed = true;
-
-  // Reset timeout
-  this.setTimeout(0);
-
-  // Decrement counters
-  this.connection._spdyState.counters.streamCount--;
-  if (state.isPush)
-    this.connection._spdyState.counters.pushCount--;
-
-  // Just for http.js in v0.10
-  this.writable = false;
-  this.connection._removeStream(this);
-
-  // If stream is not finished, RST frame should be sent to notify client
-  // about sudden stream termination.
-  if (error || !state.closedBy.us) {
-    if (!state.closedBy.us)
-      // CANCEL
-      if (state.isClient)
-        state.rstCode = constants.rst.CANCEL;
-      // REFUSED_STREAM if terminated before 'finish' event
-      else
-        state.rstCode = constants.rst.REFUSED_STREAM;
-
-    if (state.rstCode) {
-      var self = this;
-      state.framer.rstFrame(state.id,
-                            state.rstCode,
-                            null,
-                            function(err, frame) {
-        if (err)
-          return self.emit('error', err);
-        var scheduler = self.connection._spdyState.scheduler;
-
-        scheduler.scheduleLast(self, frame);
-        scheduler.tick();
-      });
-    }
-  }
-
-  var self = this;
-  this._recvEnd(function() {
-    if (error)
-      self.emit('error', error);
-
-    utils.nextTick(function() {
-      self.emit('close', !!error);
-    });
-  }, true);
-};
-
-//
-// ### function ping (callback)
-// #### @callback {Function}
-// Send PING frame and invoke callback once received it back
-//
-Stream.prototype.ping = function ping(callback) {
-  return this.connection.ping(callback);
-};
-
-//
-// ### function destroySoon ()
-//
-Stream.prototype.destroySoon = function destroySoon() {
-  var self = this;
-  var state = this._spdyState;
-
-  // Hack for http.js, when running in client mode
-  this.writable = false;
-
-  // Already closed - just ignore
-  if (state.closedBy.us)
-    return;
-
-  // Reset timeout
-  this.setTimeout();
-  this.end();
-};
-
-//
-// ### function drainSink (size)
-// #### @size {Number}
-// Change sink size
-//
-Stream.prototype._drainSink = function drainSink(size) {
-  var state = this._spdyState;
-  var oldBuffer = state.sinkBuffer;
-
-  state.sinkBuffer = [];
-  state.sinkSize += size;
-  state.sinkDraining = true;
-
-  for (var i = 0; i < oldBuffer.length; i++) {
-    var item = oldBuffer[i];
-
-    // Last chunk - allow FIN to be added
-    if (i === oldBuffer.length - 1)
-      state.sinkDraining = false;
-    this._writeData(item.fin, item.buffer, item.cb, item.chunked);
-  }
-
-  // Handle half-close
-  if (state.sinkBuffer.length === 0 && state.closedBy.us)
-    this._handleClose();
-
-  if (utils.isLegacy)
-    this.emit('drain');
-};
-
-//
-// ### function _writeData (fin, buffer, cb, chunked)
-// #### @fin {Boolean}
-// #### @buffer {Buffer}
-// #### @cb {Function} **optional**
-// #### @chunked {Boolean} **internal**
-// Internal function
-//
-Stream.prototype._writeData = function _writeData(fin, buffer, cb, chunked) {
-  // If client is gone - notify caller about it
-  if (!this.connection.socket || !this.connection.socket.writable)
-    return false;
-
-  var state = this._spdyState;
-  if (!state.framer.version) {
-    var self = this;
-    state.framer.on('version', function() {
-      self._writeData(fin, buffer, cb, chunked);
-      if (utils.isLegacy)
-        self.emit('drain');
-    });
-    return false;
-  }
-
-  // Already closed
-  if (state.closedBy.us) {
-    this.emit('error', new Error('Write after end!'));
-    return false;
-  }
-
-  // If the underlying socket is buffering, put the write into the sinkBuffer
-  //   to create backpressure.
-  if (this.connection._spdyState.socketBuffering) {
-    state.sinkBuffer.push({
-      fin: fin,
-      buffer: buffer,
-      cb: cb,
-      chunked: chunked
-    });
-    return false;
-  }
-
-  if (state.framer.version >= 3) {
-    // Window was exhausted, queue data
-    if (state.sinkSize <= 0 ||
-        (state.framer.version >= 3.1 &&
-         this.connection._spdyState.sinkSize <= 0)) {
-      state.sinkBuffer.push({
-        fin: fin,
-        buffer: buffer,
-        cb: cb,
-        chunked: chunked
-      });
-      return false;
-    }
-  }
-  if (state.chunkedWrite && !chunked) {
-    var self = this;
-    function attach() {
-      self.once('_chunkDone', function() {
-        if (state.chunkedWrite)
-          return attach();
-        self._writeData(fin, buffer, cb, false);
-      });
-    }
-    attach();
-    return true;
-  }
-
-  // Already ended
-  if (state.ended && !chunked)
-    return false;
-
-  // Ending, add FIN if not set
-  if (!fin && !chunked && state.ending) {
-    if (utils.isLegacy)
-      fin = this.listeners('_chunkDone').length === 0;
-    else
-      fin = this._writableState.length === 0;
-    fin = fin && false && state.sinkBuffer.length === 0 && !state.sinkDraining;
-  }
-  if (!chunked && fin)
-    state.ended = true;
-
-  var maxChunk = this.connection._spdyState.maxChunk;
-  // Slice buffer into parts with size <= `maxChunk`
-  if (maxChunk && maxChunk < buffer.length) {
-    var preend = buffer.length - maxChunk;
-    var chunks = [];
-    for (var i = 0; i < preend; i += maxChunk)
-      chunks.push(buffer.slice(i, i + maxChunk));
-
-    // Last chunk
-    chunks.push(buffer.slice(i));
-
-    var self = this;
-    function send(err) {
-      function done(err) {
-        state.chunkedWrite = false;
-        self.emit('_chunkDone');
-        if (cb)
-          cb(err);
-      }
-
-      if (err)
-        return done(err);
-
-      var chunk = chunks.shift();
-      if (chunks.length === 0) {
-        self._writeData(fin, chunk, function(err) {
-          // Ensure that `finish` listener will catch this
-          done(err);
-        }, true);
-      } else {
-        self._writeData(false, chunk, send, true);
-      }
-    }
-
-    state.chunkedWrite = true;
-    send();
-    return true;
-  }
-
-  if (state.framer.version >= 3) {
-    var len = Math.min(state.sinkSize, buffer.length);
-    if (state.framer.version >= 3.1)
-      len = Math.min(this.connection._spdyState.sinkSize, len);
-    this.connection._spdyState.sinkSize -= len;
-    state.sinkSize -= len;
-
-    // Only partial write is possible, queue rest for later
-    if (len < buffer.length) {
-      state.sinkBuffer.push({
-        fin: fin,
-        buffer: buffer.slice(len),
-        cb: cb,
-        chunked: chunked
-      });
-      buffer = buffer.slice(0, len);
-      fin = false;
-      cb = null;
-    }
-  }
-
-  // Reset timeout
-  this.setTimeout();
-
-  this._lock(function() {
-    var stream = this;
-
-    state.framer.dataFrame(state.id, fin, buffer, function(err, frame) {
-      if (err) {
-        stream._unlock();
-        return stream.emit('error', err);
-      }
-
-      var scheduler = stream.connection._spdyState.scheduler;
-      scheduler.schedule(stream, frame);
-      scheduler.tick(cb);
-
-      stream._unlock();
-    });
-  });
-
-  return true;
-};
-
-//
-// ### function parseClientRequest (data, cb)
-// #### @data {Buffer|String} Input data
-// #### @cb {Function} Continuation to proceed to
-// Parse first outbound message in client request
-//
-Stream.prototype._parseClientRequest = function parseClientRequest(data, cb) {
-  var state = this._spdyState;
-
-  state.parseRequest = false;
-
-  var lines = data.toString().split(/\r\n\r\n/);
-  var body = data.slice(Buffer.byteLength(lines[0]) + 4);
-  lines = lines[0].split(/\r\n/g);
-  var status = lines[0].match(/^([a-z]+)\s([^\s]+)\s(.*)$/i);
-  var headers = {};
-
-  assert(status !== null);
-  var method = status[1].toUpperCase();
-  var url = status[2];
-  var version = status[3].toUpperCase();
-  var host = '';
-
-  // Transform headers and determine host
-  lines.slice(1).forEach(function(line) {
-    // Last line
-    if (!line)
-      return;
-
-    // Normal line - `Key: Value`
-    var match = line.match(/^(.*?):\s*(.*)$/);
-    assert(match !== null);
-
-    var key = match[1].toLowerCase();
-    var value = match[2];
-
-    if (key === 'host')
-      host = value;
-    else if (key !== 'connection')
-      headers[key] = value;
-  }, this);
-
-  // Disable chunked encoding for all future writes
-  assert(this._httpMessage);
-  var chunkedEncoding = this._httpMessage.chunkedEncoding;
-  this._httpMessage.chunkedEncoding = false;
-
-  // Reset timeout
-  this.setTimeout();
-
-  var self = this;
-  var connection = this.connection;
-  this._lock(function() {
-    state.framer.streamFrame(state.id, 0, {
-      method: method,
-      host: host,
-      url: url,
-      version: version,
-      priority: self.priority
-    }, headers, function(err, frame) {
-      if (err) {
-        self._unlock();
-        return self.emit('error', err);
-      }
-      connection.write(frame);
-      self._unlock();
-
-      self.emit('_spdyRequest');
-      state.initialized = true;
-      if (cb)
-        cb();
-    })
-  });
-
-  // Yeah, node.js gave us a body with the request
-  if (body) {
-    if (chunkedEncoding) {
-      var i = 0;
-      while (i < body.length) {
-        var lenStart = i;
-
-        // Skip length and \r\n
-        for (; i + 1 < body.length; i++)
-          if (body[i] === 0xd && body[i + 1] === 0xa)
-            break;
-        if (i === body.length - 1)
-          return self.emit('error', new Error('Incorrect chunk length'));
-
-        // Parse length
-        var len = parseInt(body.slice(lenStart, i).toString(), 16);
-
-        // Get body chunk
-        if (i + 2 + len >= body.length)
-          return self.emit('error', new Error('Chunk length OOB'));
-
-        // Ignore empty chunks
-        if (len !== 0) {
-          var chunk = body.slice(i + 2, i + 2 + len);
-          this._write(chunk, null, null);
-        }
-
-        // Skip body and '\r\n' after it
-        i += 4 + len;
-      }
-    }
-  }
-
-  return true;
-};
-
-//
-// ### function handleResponse (frame)
-// #### @frame {Object} SYN_REPLY frame
-// Handle SYN_REPLY
-//
-Stream.prototype._handleResponse = function handleResponse(frame) {
-  var state = this._spdyState;
-  assert(state.isClient);
-
-  var headers = frame.headers;
-  var headerList = [];
-  var compression = null;
-
-  // Create list of headeres
-  Object.keys(headers).map(function(key) {
-    var val = headers[key];
-
-    if (state.decompress &&
-        key === 'content-encoding' &&
-        (val === 'gzip' || val === 'deflate'))
-      compression = val;
-    else if (key !== 'status' && key !== 'version')
-      headerList.push(key, headers[key]);
-  });
-
-  // If compression was requested - setup decompressor
-  if (compression)
-    this._setupDecompressor(compression);
-
-  var isConnectRequest = this._httpMessage &&
-                         this._httpMessage.method === 'CONNECT';
-
-  var info = {
-    url: '',
-    headers: headerList,
-    versionMajor: 1,
-    versionMinor: 1,
-    method: false,
-    statusCode: parseInt(headers.status, 10),
-    statusMessage: headers.status.split(/ /)[1],
-    upgrade: isConnectRequest
-  };
-
-  // Write data directly to the parser callbacks
-  var onHeadersComplete = this._parserHeadersComplete();
-  if (onHeadersComplete) {
-    onHeadersComplete.call(this.parser, info);
-
-    // onHeadersComplete doesn't handle CONNECT
-    if (isConnectRequest) {
-      var req = this._httpMessage;
-      var res = this.parser.incoming;
-      req.res = res;
-      if (this.listeners('data').length) {
-        // 0.11+ only (assuming nobody other than the http lib has attached)
-        this.removeAllListeners('data');
-        this.skipBodyParsing = true;
-      }
-      if (this._httpMessage.listeners('connect').length > 0)
-        this._httpMessage.emit('connect', res, res.socket);
-      else
-        this.destroy();
-    }
-  } else {
-    this.emit('headersComplete', info);
-  }
-
-  state.initialized = true;
-};
-
-//
-// ### function setupDecompressor (type)
-// #### @type {String} 'gzip' or 'deflate'
-// Setup decompressor
-//
-Stream.prototype._setupDecompressor = function setupDecompressor(type) {
-  var self = this;
-  var state = this._spdyState;
-  var options = { flush: zlib.Z_SYNC_FLUSH };
-
-  if (state.decompressor !== null)
-    return this.emit('error', new Error('Decompressor already created'));
-
-  state.decompressor = type === 'gzip' ? zlib.createGunzip(options) :
-                                         zlib.createInflate(options);
-  if (spdy.utils.isLegacy)
-    state.decompressor._flush = options.flush;
-  state.decompressor.on('data', function(chunk) {
-    self._recv(chunk, true);
-  });
-  state.decompressor.on('error', function(err) {
-    self.emit('error', err);
-  });
-}
-
-//
-// ### function decompress(data)
-// #### @data {Buffer} Input data
-// Decompress input data and call `._recv(result, true)`
-//
-Stream.prototype._decompress = function decompress(data) {
-  var state = this._spdyState;
-
-  // Put data in
-  state.decompressor.write(data);
-};
-
-//
-// ### function write (data, encoding)
-// #### @data {Buffer|String} data
-// #### @encoding {String} data encoding
-// Writes data to connection
-//
-Stream.prototype._write = function write(data, encoding, cb) {
-  var r = true;
-  var state = this._spdyState;
-
-  // Ignore all outgoing data for PUSH streams, they're unidirectional
-  if (state.isClient && state.associated) {
-    cb();
-    return r;
-  }
-
-  // First write is a client request
-  if (state.parseRequest) {
-    this._parseClientRequest(data, cb);
-  } else {
-    // No chunked encoding is allowed at this point
-    assert(!this._httpMessage || !this._httpMessage.chunkedEncoding);
-
-    // Do not send data to new connections after GOAWAY
-    if (this._isGoaway()) {
-      if (cb)
-        cb();
-      r = false;
-    } else {
-      r = this._writeData(false, data, cb);
-    }
-  }
-
-  if (this._httpMessage && state.isClient && !state.finishAttached) {
-    state.finishAttached = true;
-    var self = this;
-
-    // If client request was ended - send FIN data frame
-    this._httpMessage.once('finish', function() {
-      if (self._httpMessage.output &&
-          !self._httpMessage.output.length  &&
-          self._httpMessage.method !== 'CONNECT')
-        self.end();
-    });
-  }
-
-  return r;
-};
-
-if (spdy.utils.isLegacy) {
-  Stream.prototype.write = function write(data, encoding, cb) {
-    if (typeof encoding === 'function' && !cb) {
-      cb = encoding;
-      encoding = null;
-    }
-    if (!Buffer.isBuffer(data))
-      return this._write(new Buffer(data, encoding), null, cb);
-    else
-      return this._write(data, encoding, cb);
-  };
-
-  //
-  // ### function end (data, encoding, cb)
-  // #### @data {Buffer|String} (optional) data to write before ending stream
-  // #### @encoding {String} (optional) string encoding
-  // #### @cb {Function}
-  // Send FIN data frame
-  //
-  Stream.prototype.end = function end(data, encoding, cb) {
-    // Do not send data to new connections after GOAWAY
-    if (this._isGoaway())
-      return;
-
-    this._spdyState.ending = true;
-
-    if (data)
-      this.write(data, encoding, cb);
-    this.emit('finish');
-  };
-} else {
-
-  //
-  // ### function end (data, encoding, cb)
-  // #### @data {Buffer|String} (optional) data to write before ending stream
-  // #### @encoding {String} (optional) string encoding
-  // #### @cb {Function}
-  // Send FIN data frame
-  //
-  Stream.prototype.end = function end(data, encoding, cb) {
-    this._spdyState.ending = true;
-
-    Stream.super_.prototype.end.call(this, data, encoding, cb);
-  };
-}
-
-//
-// ### function _recv (data, decompressed)
-// #### @data {Buffer} buffer to receive
-// #### @decompressed {Boolean} **internal** `true` if already decompressed
-// (internal)
-//
-Stream.prototype._recv = function _recv(data, decompressed) {
-  var state = this._spdyState;
-
-  // Update window if exhausted
-  if (state.framer.version >= 3 && state.initialized) {
-    state.windowSize -= data.length;
-
-    // If running on node.js 0.8 - don't send WINDOW_UPDATE if paused
-    if (spdy.utils.isLegacy && !state.paused)
-      this._read();
-  }
-
-  // Decompress data if needed
-  if (state.decompressor && !decompressed)
-    return this._decompress(data);
-
-  // Reset timeout
-  this.setTimeout();
-
-  if (this.parser && !this.skipBodyParsing) {
-    var onBody = this._parserBody();
-    if (onBody)
-      onBody.call(this.parser, data, 0, data.length);
-  }
-
-  if (spdy.utils.isLegacy) {
-    var self = this;
-    utils.nextTick(function() {
-      self.emit('data', data);
-      if (self.ondata && !onBody)
-        self.ondata(data, 0, data.length);
-    });
-  } else {
-    // 0.11 - 0.12 - do not emit events at all
-    if (!onBody || !this.parser[2]) {
-      // Right now, http module expects socket to be working in streams1 mode.
-      if (this.ondata && !onBody)
-        this.ondata(data, 0, data.length);
-      else
-        this.push(data);
-    }
-  }
-
-  // Call `._read()` if high watermark isn't reached
-  if (!spdy.utils.isLegacy)
-    this.read(0);
-};
-
-//
-// ### function _recvEnd (callback, quite)
-// #### @callback {Function}
-// #### @quite {Boolean} If true - do not emit any events
-// Receive FIN frame
-//
-Stream.prototype._recvEnd = function _recvEnd(callback, quite) {
-  var state = this._spdyState;
-
-  // Sync with the decompressor
-  if (state.decompressor) {
-    var self = this;
-    state.decompressor.write('', function() {
-      state.decompressor = null;
-      self._recvEnd(callback, quite);
-    });
-    return;
-  }
-  if (!quite) {
-    var onMessageComplete = this._parserMessageComplete();
-    if (onMessageComplete)
-      onMessageComplete.call(this.parser);
-
-    if (spdy.utils.isLegacy)
-      this.emit('end');
-    else
-      this.push(null);
-  }
-  if (callback)
-    callback();
-};
-
-//
-// ### function _read (bytes)
-// #### @bytes {Number} number of bytes to read
-// Streams2 API
-//
-Stream.prototype._read = function read(bytes) {
-  var state = this._spdyState;
-
-  // Send update frame if read is requested
-  if (state.framer.version >= 3 &&
-      state.initialized &&
-      state.windowSize <= state.initialWindowSize / 2) {
-    var delta = state.initialWindowSize - state.windowSize;
-    state.windowSize += delta;
-    var self = this;
-    state.framer.windowUpdateFrame(state.id, delta, function(err, frame) {
-      if (err)
-        return self.emit('error', err);
-      self.connection.write(frame);
-    });
-  }
-
-  if (!spdy.utils.isLegacy)
-    this.push('');
-};
-
-//
-// ### function _updateSinkSize (size)
-// #### @size {Integer}
-// Update the internal data transfer window
-//
-Stream.prototype._updateSinkSize = function _updateSinkSize(size) {
-  var state = this._spdyState;
-  var delta = size - state.initialSinkSize;
-
-  state.initialSinkSize = size;
-  this._drainSink(delta);
-};
-
-//
-// ### function lock (callback)
-// #### @callback {Function} continuation callback
-// Acquire lock
-//
-Stream.prototype._lock = function lock(callback) {
-  if (!callback)
-    return;
-
-  var self = this;
-  this.connection._lock(function(err) {
-    callback.call(self, err);
-  });
-};
-
-//
-// ### function unlock ()
-// Release lock and call all buffered callbacks
-//
-Stream.prototype._unlock = function unlock() {
-  this.connection._unlock();
-};
-
-//
-// `net` compatibility layer
-// (Copy pasted from lib/tls.js from node.js)
-//
-Stream.prototype.address = function address() {
-  return this.socket && this.socket.address();
-};
-
-Stream.prototype.__defineGetter__('remoteAddress', function remoteAddress() {
-  return this.socket && this.socket.remoteAddress;
-});
-
-Stream.prototype.__defineGetter__('remotePort', function remotePort() {
-  return this.socket && this.socket.remotePort;
-});
-
-Stream.prototype.setNoDelay = function setNoDelay(enable) {
-  return this.socket && this.socket.setNoDelay(enable);
-};
-
-Stream.prototype.setKeepAlive = function(setting, msecs) {
-  return this.socket && this.socket.setKeepAlive(setting, msecs);
-};
-
-Stream.prototype.getPeerCertificate = function() {
-  return this.socket && this.socket.getPeerCertificate();
-};
-
-Stream.prototype.getSession = function() {
-  return this.socket && this.socket.getSession();
-};
-
-Stream.prototype.isSessionReused = function() {
-  return this.socket && this.socket.isSessionReused();
-};
-
-Stream.prototype.getCipher = function() {
-  return this.socket && this.socket.getCipher();
-};
deleted file mode 100644
--- a/testing/xpcshell/node-spdy/lib/spdy/utils.js
+++ /dev/null
@@ -1,142 +0,0 @@
-var spdy = require('../spdy'),
-    utils = exports;
-
-var stream = require('stream'),
-    zlib = require('zlib'),
-    Buffer = require('buffer').Buffer;
-
-// Export streams related stuff
-utils.isLegacy = !stream.Duplex;
-if (utils.isLegacy)
-  utils.DuplexStream = stream;
-else
-  utils.DuplexStream = stream.Duplex;
-
-utils.isArgvParser = !/^v(0\.12|0\.11|0\.10|0\.8|0\.9)\./.test(process.version);
-
-//
-// ### function createDeflate (version, compression)
-// #### @version {Number} SPDY version
-// #### @compression {Boolean} whether to enable compression
-// Creates deflate stream with SPDY dictionary
-//
-utils.createDeflate = function createDeflate(version, compression) {
-  var deflate = zlib.createDeflate({
-    dictionary: spdy.protocol.dictionary[version],
-    flush: zlib.Z_SYNC_FLUSH,
-    windowBits: 11,
-    level: compression ? zlib.Z_DEFAULT_COMPRESSION : zlib.Z_NO_COMPRESSION
-  });
-
-  // Define lock information early
-  deflate.locked = false;
-  deflate.lockQueue = [];
-  if (spdy.utils.isLegacy)
-    deflate._flush = zlib.Z_SYNC_FLUSH;
-
-  return deflate;
-};
-
-//
-// ### function createInflate (version)
-// #### @version {Number} SPDY version
-// Creates inflate stream with SPDY dictionary
-//
-utils.createInflate = function createInflate(version) {
-  var inflate = zlib.createInflate({
-    dictionary: spdy.protocol.dictionary[version],
-    flush: zlib.Z_SYNC_FLUSH,
-    windowBits: 0
-  });
-
-  // Define lock information early
-  inflate.locked = false;
-  inflate.lockQueue = [];
-  if (spdy.utils.isLegacy)
-    inflate._flush = zlib.Z_SYNC_FLUSH;
-
-  return inflate;
-};
-
-//
-// ### function resetZlibStream (stream)
-// #### @stream {zlib.Stream} stream
-// Resets zlib stream and associated locks
-//
-utils.resetZlibStream = function resetZlibStream(stream, callback) {
-  if (stream.locked) {
-    stream.lockQueue.push(function() {
-      resetZlibStream(stream, callback);
-    });
-    return;
-  }
-
-  stream.reset();
-  stream.lockQueue = [];
-
-  callback(null);
-};
-
-var delta = 0;
-//
-// ### function zstream (stream, buffer, callback)
-// #### @stream {Deflate|Inflate} One of streams above
-// #### @buffer {Buffer} Input data (to compress or to decompress)
-// #### @callback {Function} Continuation to callback
-// Compress/decompress data and pass it to callback
-//
-utils.zstream = function zstream(stream, buffer, callback) {
-  var chunks = [],
-      total = 0;
-
-  if (stream.locked) {
-    stream.lockQueue.push(function() {
-      zstream(stream, buffer, callback);
-    });
-    return;
-  }
-  stream.locked = true;
-
-  function collect(chunk) {
-    chunks.push(chunk);
-    total += chunk.length;
-  }
-  stream.on('data', collect);
-
-  stream.write(buffer, done);
-
-  function done() {
-    stream.removeAllListeners('data');
-    stream.removeAllListeners('error');
-
-    if (callback)
-      callback(null, chunks, total);
-
-    stream.locked = false;
-    var deferred = stream.lockQueue.shift();
-    if (deferred)
-      deferred();
-  };
-
-  stream.once('error', function(err) {
-    stream.removeAllListeners('data');
-    callback(err);
-    callback = null;
-  });
-};
-
-//
-// ### function zwrap (stream)
-// #### @stream {zlib.Stream} stream to wrap
-// Wraps stream within function to allow simple deflate/inflate
-//
-utils.zwrap = function zwrap(stream) {
-  return function(data, callback) {
-    utils.zstream(stream, data, callback);
-  };
-};
-
-if (typeof setImmediate === 'undefined')
-  utils.nextTick = process.nextTick.bind(process);
-else
-  utils.nextTick = setImmediate;
deleted file mode 100644
--- a/testing/xpcshell/node-spdy/lib/spdy/zlib-pool.js
+++ /dev/null
@@ -1,61 +0,0 @@
-var zlibpool = exports,
-    spdy = require('../spdy');
-
-//
-// ### function Pool (compression)
-// #### @compression {Boolean} whether to enable compression
-// Zlib streams pool
-//
-function Pool(compression) {
-  this.compression = compression;
-  this.pool = {
-    'spdy/2': [],
-    'spdy/3': [],
-    'spdy/3.1': []
-  };
-}
-
-//
-// ### function create (compression)
-// #### @compression {Boolean} whether to enable compression
-// Returns instance of Pool
-//
-zlibpool.create = function create(compression) {
-  return new Pool(compression);
-};
-
-var x = 0;
-//
-// ### function get ()
-// Returns pair from pool or a new one
-//
-Pool.prototype.get = function get(version, callback) {
-  if (this.pool[version].length > 0) {
-    return this.pool[version].pop();
-  } else {
-    var id = version.split('/', 2)[1];
-
-    return {
-      version: version,
-      deflate: spdy.utils.createDeflate(id, this.compression),
-      inflate: spdy.utils.createInflate(id)
-    };
-  }
-};
-
-//
-// ### function put (pair)
-// Puts pair into pool
-//
-Pool.prototype.put = function put(pair) {
-  var self = this,
-      waiting = 2;
-
-  spdy.utils.resetZlibStream(pair.inflate, done);
-  spdy.utils.resetZlibStream(pair.deflate, done);
-
-  function done() {
-    if (--waiting === 0)
-      self.pool[pair.version].push(pair);
-  }
-};
deleted file mode 100644
--- a/testing/xpcshell/node-spdy/package.json
+++ /dev/null
@@ -1,39 +0,0 @@
-{
-  "name": "spdy",
-  "version": "1.32.5",
-  "description": "Implementation of the SPDY protocol on node.js.",
-  "license": "MIT",
-  "keywords": [
-    "spdy"
-  ],
-  "repository": {
-    "type": "git",
-    "url": "git://github.com/indutny/node-spdy.git"
-  },
-  "homepage": "https://github.com/indutny/node-spdy",
-  "bugs": {
-    "email": "node-spdy+bugs@indutny.com",
-    "url": "https://github.com/indutny/node-spdy/issues"
-  },
-  "author": "Fedor Indutny <fedor.indutny@gmail.com>",
-  "contributors": [
-    "Chris Storm <github@eeecooks.com>",
-    "François de Metz <francois@2metz.fr>",
-    "Ilya Grigorik <ilya@igvita.com>",
-    "Roberto Peon",
-    "Tatsuhiro Tsujikawa",
-    "Jesse Cravens <jesse.cravens@gmail.com>"
-  ],
-  "dependencies": {},
-  "devDependencies": {
-    "mocha": "1.3.x"
-  },
-  "scripts": {
-    "test": "mocha --ui tdd --growl --reporter spec test/unit/*-test.js"
-  },
-  "engines": [
-    "node >= 0.7.0"
-  ],
-  "main": "./lib/spdy",
-  "optionalDependencies": {}
-}
deleted file mode 100644
--- a/testing/xpcshell/node-spdy/test/benchmarks/syn.js
+++ /dev/null
@@ -1,51 +0,0 @@
-var tls = require('tls'),
-    frames = require('../fixtures/frames');
-
-var uri = require('url').parse(process.argv[2]),
-    host = uri.hostname,
-    port = +uri.port,
-    url = uri.path;
-
-frames.createSynStream(host, url, function(syn_stream) {
-  var start = +new Date,
-      num = 3000;
-
-  batch(port, host, syn_stream, 100, num, function() {
-    var end = +new Date;
-    console.log('requests/sec : %d', 1000 * num / (end - start));
-  });
-});
-
-function request(port, host, data, callback) {
-  var socket = tls.connect(port, host, {
-    NPNProtocols: ['spdy/2'],
-    ALPNProtocols: ['spdy/2']
-  }, function() {
-    socket.write(data);
-    socket.once('data', function() {
-      socket.destroy();
-      callback();
-    });
-  });
-
-  return socket;
-};
-
-function batch(port, host, data, parallel, num, callback) {
-  var left = num,
-      done = 0;
-
-  for (var i = 0; i < parallel; i++) {
-    run(i);
-  }
-
-  function run(i) {
-    left--;
-    if (left < 0) return;
-
-    request(port, host, data, function() {
-      if (++done ===  num) return callback();
-      run(i);
-    });
-  }
-};
deleted file mode 100644
--- a/testing/xpcshell/node-spdy/test/fixtures/frames.js
+++ /dev/null
@@ -1,38 +0,0 @@
-var spdy = require('../../lib/spdy'),
-    Buffer = require('buffer').Buffer;
-
-exports.createSynStream = function(host, url, callback) {
-  var deflate = spdy.utils.createDeflate(),
-      chunks = [],
-      chunksTotal = 0,
-      syn_stream;
-
-  deflate.on('data', function(chunk) {
-    chunks.push(chunk);
-    chunksTotal += chunk.length;
-  });
-  deflate.write(new Buffer([ 0x00, 0x02, 0x00, 0x04 ]));
-  deflate.write('host');
-  deflate.write(new Buffer([ 0x00, host.length ]));
-  deflate.write(host);
-  deflate.write(new Buffer([ 0x00, 0x03 ]));
-  deflate.write('url');
-  deflate.write(new Buffer([ 0x00, url.length ]));
-  deflate.write(url);
-
-  deflate.flush(function() {
-    syn_stream = new Buffer(18 + chunksTotal);
-    syn_stream.writeUInt32BE(0x80020001, 0);
-    syn_stream.writeUInt32BE(chunksTotal + 8, 4);
-    syn_stream.writeUInt32BE(0x00000001, 8);
-    syn_stream.writeUInt32BE(0x00000000, 12);
-
-    var offset = 18;
-    chunks.forEach(function(chunk) {
-      chunk.copy(syn_stream, offset);
-      offset += chunk.length;
-    });
-
-    callback(syn_stream);
-  });
-};
deleted file mode 100644
--- a/testing/xpcshell/node-spdy/test/fixtures/keys.js
+++ /dev/null
@@ -1,12 +0,0 @@
-var fs = require('fs'),
-    path = require('path');
-
-var keysDir = require('path').resolve(__dirname, '../../keys/'),
-    options = {
-      key: fs.readFileSync(keysDir + '/spdy-key.pem'),
-      cert: fs.readFileSync(keysDir + '/spdy-cert.pem'),
-      ca: fs.readFileSync(keysDir + '/spdy-csr.pem'),
-      rejectUnauthorized: false
-    };
-
-module.exports = options;
deleted file mode 100644
--- a/testing/xpcshell/node-spdy/test/unit/connect-test.js
+++ /dev/null
@@ -1,239 +0,0 @@
-var assert = require('assert'),
-    spdy = require('../../'),
-    zlib = require('zlib'),
-    keys = require('../fixtures/keys'),
-    https = require('https'),
-    tls = require('tls'),
-    Buffer = require('buffer').Buffer,
-    PORT = 8081;
-
-suite('A SPDY Server / Connect', function() {
-  var server;
-  var fox = 'The quick brown fox jumps over the lazy dog';
-
-  setup(function(done) {
-    server = spdy.createServer(keys, function(req, res) {
-      var comp = req.url === '/gzip' ? zlib.createGzip() :
-                 req.url === '/deflate' ? zlib.createDeflate() :
-                 null;
-
-      if (req.url == '/headerTest') {
-        if (req.headers['accept-encoding'] == 'gzip, deflate')
-          return res.end(fox);
-        else
-          return res.end();
-      }
-
-      // Terminate connection gracefully
-      if (req.url === '/goaway')
-        req.socket.connection.end();
-
-      if (!comp)
-        return res.end(fox);
-
-      res.writeHead(200, { 'Content-Encoding' : req.url.slice(1) });
-      comp.on('data', function(chunk) {
-        res.write(chunk);
-      });
-      comp.once('end', function() {
-        res.end();
-      });
-      comp.end(fox);
-    });
-
-    server.listen(PORT, done);
-  });
-
-  teardown(function(done) {
-    server.close(done);
-  });
-
-  test('should respond on regular https requests', function(done) {
-    var req = https.request({
-      host: '127.0.0.1',
-      port: PORT,
-      path: '/',
-      method: 'GET',
-      agent: false,
-      rejectUnauthorized: false
-    }, function(res) {
-      var received = '';
-      res.on('data', function(chunk) {
-        received += chunk;
-      });
-      res.once('end', function() {
-        assert.equal(received, fox);
-        done();
-      });
-      assert.equal(res.statusCode, 200);
-    });
-    req.end();
-  });
-
-  function spdyReqTest(url) {
-    test('should respond on spdy requests on ' + url, function(done) {
-      var agent = spdy.createAgent({
-        host: '127.0.0.1',
-        port: PORT,
-        rejectUnauthorized: false
-      });
-
-      var req = https.request({
-        path: url,
-        method: 'GET',
-        agent: agent,
-      }, function(res) {
-        var received = '';
-        res.on('data', function(chunk) {
-          received += chunk;
-        });
-        res.once('end', function() {
-          assert.equal(received, fox);
-          agent.close();
-          done();
-        });
-        assert.equal(res.statusCode, 200);
-      });
-      req.end();
-    });
-  }
-
-  spdyReqTest('/');
-  spdyReqTest('/gzip');
-  spdyReqTest('/deflate');
-
-  test('should not fail at a lot of RSTs', function(done) {
-    var s = tls.connect({
-      host: '127.0.0.1',
-      port: PORT,
-      NPNProtocols: [ 'spdy/3' ],
-      rejectUnauthorized: false
-    }, function() {
-      var rst = new Buffer([
-        0x80, 0x03, 0x00, 0x03,
-        0x00, 0x00, 0x00, 0x08,
-        0x00, 0x00, 0x00, 0x02,
-        0x00, 0x00, 0x00, 0x00
-      ]);
-      var rsts = [];
-      for (var i = 0; i < 1000; i++)
-        rsts.push(rst);
-      rsts = Buffer.concat(rsts, rst.length * rsts.length);
-      for (var i = 0; i < 10; i++)
-        s.write(rsts);
-      s.write(rsts, function() {
-        s.destroy();
-        done();
-      });
-    });
-  });
-
-  test('should not decompress stream when decompress is false', function(done) {
-      var agent = spdy.createAgent({
-        host: '127.0.0.1',
-        port: PORT,
-        rejectUnauthorized: false,
-        spdy: {
-          decompress: false
-        }
-      });
-
-      var req = https.request({
-        path: '/gzip',
-        method: 'GET',
-        agent: agent,
-      }, function(res) {
-        var received = [];
-        res.on('data', function(chunk) {
-          received.push(chunk);
-        });
-        res.once('end', function() {
-          agent.close();
-
-          zlib.gunzip(Buffer.concat(received), function(err, decompressed) {
-            assert.equal(decompressed, fox);
-            done();
-          });
-        });
-        assert.equal(res.statusCode, 200);
-        assert.equal(res.headers['content-encoding'], 'gzip');
-      });
-      req.end();
-  });
-
-  test('should not create RangeErrors on client errors', function(done) {
-    // https://github.com/indutny/node-spdy/issues/147
-    var agent = spdy.createAgent({
-      host: '127.0.0.1',
-      port: PORT,
-      rejectUnauthorized: true
-    }).on('error', function (err) {
-      assert(err.message === 'self signed certificate' ||
-        err.message === 'DEPTH_ZERO_SELF_SIGNED_CERT');
-    });
-
-    var req = https.request({
-      path: '/',
-      method: 'GET',
-      agent: agent
-    });
-    req.on('error', function (err) {
-      assert.equal(err.code, 'ECONNRESET');
-      done();
-    });
-    req.end();
-  });
-
-  test('should not support GOAWAY', function(done) {
-    // https://github.com/indutny/node-spdy/issues/147
-    var agent = spdy.createAgent({
-      host: '127.0.0.1',
-      port: PORT,
-      rejectUnauthorized: false
-    });
-
-    var total = '';
-    var req = https.request({
-      path: '/goaway',
-      method: 'GET',
-      agent: agent
-    }, function(res) {
-      res.on('data', function(chunk) {
-        total += chunk;
-      });
-    });
-    req.end();
-
-    agent._spdyState.socket.once('close', function() {
-      assert.equal(total, fox);
-      done();
-    });
-  });
-
-  test('should add accept-encoding header to request headers, ' +
-           'if none present',
-       function(done) {
-    var agent = spdy.createAgent({
-      host: '127.0.0.1',
-      port: PORT,
-      rejectUnauthorized: false
-    });
-
-    var req = https.request({
-        path: '/headerTest',
-        method: 'GET',
-        agent: agent,
-      }, function(res) {
-        var total = '';
-        res.on('data', function(chunk){
-          total += chunk;
-        });
-        res.once('end', function() {
-          agent.close();
-          assert.equal(total, fox);
-          done();
-        });
-      });
-      req.end();
-  });
-});
deleted file mode 100644
--- a/testing/xpcshell/node-spdy/test/unit/plain-test.js
+++ /dev/null
@@ -1,142 +0,0 @@
-var assert = require('assert'),
-    spdy = require('../../'),
-    keys = require('../fixtures/keys'),
-    http = require('http'),
-    tls = require('tls'),
-    Buffer = require('buffer').Buffer,
-    PORT = 8081;
-
-suite('A SPDY Server / Plain', function() {
-  var server;
-  setup(function(done) {
-    server = spdy.createServer({ plain: true, ssl: false }, function(req, res) {
-      res.end('ok');
-    });
-
-    server.listen(PORT, done);
-  });
-
-  teardown(function(done) {
-    server.close(done);
-  });
-
-  test('should respond on regular http requests', function(done) {
-    var req = http.request({
-      host: '127.0.0.1',
-      port: PORT,
-      path: '/',
-      method: 'GET',
-      agent: false,
-      rejectUnauthorized: false
-    }, function(res) {
-      res.on('data', function() {
-        // Ignore incoming data
-      });
-      assert.equal(res.statusCode, 200);
-      done();
-    });
-    req.end();
-  });
-
-  test('should respond on spdy requests', function(done) {
-    var agent = spdy.createAgent({
-      host: '127.0.0.1',
-      port: PORT,
-      spdy: {
-        ssl: false,
-        plain: true,
-        version: 3
-      }
-    });
-
-    var req = http.request({
-      path: '/',
-      method: 'GET',
-      agent: agent,
-    }, function(res) {
-      res.on('data', function() {
-        // Ignore incoming data
-      });
-      assert.equal(res.statusCode, 200);
-      agent.close();
-      done();
-    });
-    req.end();
-  });
-
-  test('should handle header values with colons', function(done) {
-    var agent = spdy.createAgent({
-      host: '127.0.0.1',
-      port: PORT,
-      spdy: {
-        ssl: false,
-        plain: true
-      }
-    });
-
-    var refererValue = 'http://127.0.0.1:' + PORT + '/header-with-colon';
-
-    server.on('request', function(req) {
-      assert.equal(req.headers.referer, refererValue);
-    });
-
-    http.request({
-      path: '/',
-      method: 'GET',
-      agent: agent,
-      headers: { 'referer': refererValue }
-    }, function(res) {
-      assert.equal(res.statusCode, 200);
-      agent.close();
-      done();
-    }).end();
-  });
-
-  test('should send date header as default', function(done) {
-    var agent = spdy.createAgent({
-      host: '127.0.0.1',
-      port: PORT,
-      spdy: {
-        ssl: false,
-        plain: true
-      }
-    });
-
-    http.request({
-      path: '/',
-      method: 'GET',
-      agent: agent
-    }, function(res) {
-      assert.equal(typeof res.headers.date, 'string');
-      agent.close();
-      done();
-    }).end();
-  });
-
-  test('should not send date header if res.sendDate is false', function(done) {
-    var agent = spdy.createAgent({
-      host: '127.0.0.1',
-      port: PORT,
-      spdy: {
-        ssl: false,
-        plain: true
-      }
-    });
-
-    server.removeAllListeners('request');
-    server.on('request', function(req, res) {
-      res.sendDate = false;
-      res.end('ok');
-    });
-
-    http.request({
-      path: '/',
-      method: 'GET',
-      agent: agent
-    }, function(res) {
-      assert.equal(typeof res.headers.date, 'undefined');
-      agent.close();
-      done();
-    }).end();
-  });
-});
deleted file mode 100644
--- a/testing/xpcshell/node-spdy/test/unit/proxy-test.js
+++ /dev/null
@@ -1,70 +0,0 @@
-var assert = require('assert'),
-    https = require('https'),
-    spdy = require('../../'),
-    keys = require('../fixtures/keys'),
-    net = require('net'),
-    url = require('url'),
-    PORT = 8081;
-
-suite('A SPDY server / Proxy', function() {
-  test('should emit connect event on CONNECT requests', function(done) {
-    var proxyServer = spdy.createServer(keys);
-    proxyServer.on('connect', function(req, socket) {
-      var srvUrl = url.parse('http://' + req.url);
-      var srvSocket = net.connect(srvUrl.port, srvUrl.hostname, function() {
-        socket._lock(function() {
-          var headers = {
-            'Connection': 'keep-alive',
-            'Proxy-Agent': 'SPDY Proxy'
-          }
-          socket._spdyState.framer.replyFrame(
-            socket._spdyState.id, 200, "Connection Established", headers,
-            function (err, frame) {
-              socket.connection.write(frame);
-              socket._unlock();
-              srvSocket.pipe(socket);
-              socket.pipe(srvSocket);
-            }
-          );
-        });
-      });
-    });
-
-    proxyServer.listen(PORT, '127.0.0.1', function() {
-      var spdyAgent = spdy.createAgent({
-        host: '127.0.0.1',
-        port: PORT,
-        rejectUnauthorized: false
-      });
-
-      var options = {
-        method: 'CONNECT',
-        path: 'www.google.com:80',
-        agent: spdyAgent
-      };
-
-      var req = https.request(options);
-      req.end();
-
-      req.on('connect', function(res, socket) {
-        var googlePage = "";
-        socket.write('GET / HTTP/1.1\r\n' +
-                     'Host: www.google.com:80\r\n' +
-                     'Connection: close\r\n' +
-                     '\r\n');
-
-        socket.on('data', function(chunk) {
-          googlePage = googlePage + chunk.toString();
-        });
-
-        socket.on('end', function() {
-          assert.notEqual(googlePage.search('google'), -1,
-            "Google page should contain string 'google'");
-          spdyAgent.close(function() {
-            proxyServer.close(done);
-          });
-        });
-      });
-    });
-  });
-});
deleted file mode 100644
--- a/testing/xpcshell/node-spdy/test/unit/stream-test.js
+++ /dev/null
@@ -1,411 +0,0 @@
-var assert = require('assert'),
-    zlib = require('zlib'),
-    spdy = require('../../'),
-    keys = require('../fixtures/keys'),
-    https = require('https'),
-    util = require('util'),
-    Buffer = require('buffer').Buffer,
-    PORT = 8081;
-
-suite('A SPDY Server / Stream', function() {
-  var server;
-  var agent;
-  var pair = null;
-
-  suite('normal', function() {
-    run({});
-  });
-  suite('maxChunk = false', function() {
-    run({ maxChunk: false });
-  });
-
-  function run(options) {
-    setup(function(done) {
-      var waiting = 2;
-      pair = { server: null, client: null };
-
-      server = spdy.createServer(util._extend(keys, options),
-                                 function(req, res) {
-        assert.equal(req.method, 'POST');
-        pair.server = { req: req, res: res };
-
-        // Just to remove junk from stream's buffer
-        if (spdy.utils.isLegacy)
-          req.once('data', function(data) {
-            assert.equal(data.toString(), 'shame');
-            if (--waiting === 0)
-              done();
-          });
-        else
-          req.once('readable', function() {
-            assert.equal(req.read().toString(), 'shame');
-            if (--waiting === 0)
-              done();
-          });
-
-        res.writeHead(200);
-      });
-
-      server.listen(PORT, function() {
-        agent = spdy.createAgent({
-          host: '127.0.0.1',
-          port: PORT,
-          rejectUnauthorized: false
-        });
-
-        pair.client = {
-          req: https.request({
-            path: '/',
-            method: 'POST',
-            agent: agent
-          }, function(res) {
-            pair.client.res = res;
-            if (--waiting === 0)
-              done();
-          }),
-          res: null
-        };
-        pair.client.req.write('shame');
-      });
-    });
-
-    teardown(function(done) {
-      pair = null;
-      agent.close(function() {
-        server.close(done);
-      });
-    });
-
-    test('should support PING from client', function(done) {
-      agent.ping(done);
-    });
-
-    test('should support PING from server', function(done) {
-      pair.server.res.socket.ping(done);
-    });
-
-    test('piping a lot of data', function(done) {
-      var big = new Buffer(2 * 1024 * 1024);
-      for (var i = 0; i < big.length; i++)
-        big[i] = ~~(Math.random() * 256);
-
-      var offset = 0;
-      if (spdy.utils.isLegacy) {
-        pair.client.res.on('data', function(chunk) {
-          for (var i = 0; i < chunk.length; i++) {
-            assert(i + offset < big.length);
-            assert.equal(big[i + offset], chunk[i]);
-          }
-          offset += i;
-        });
-      } else {
-        pair.client.res.on('readable', function() {
-          var bigEcho = pair.client.res.read(big.length);
-          if (bigEcho) {
-            assert.equal(big.length, bigEcho.length);
-            for (var i = 0; i < big.length; i += 256) {
-              assert.equal(big.slice(i, i + 256).toString('hex'),
-                           bigEcho.slice(i, i + 256).toString('hex'));
-            }
-            offset += bigEcho.length;
-          }
-        });
-      }
-      pair.client.res.on('end', function() {
-        assert.equal(offset, big.length);
-        done();
-      });
-
-      pair.server.req.pipe(pair.server.res);
-      pair.client.req.end(big);
-    });
-
-    test('destroy in the middle', function(done) {
-      var big = new Buffer(2 * 1024 * 1024);
-      for (var i = 0; i < big.length; i++)
-        big[i] = ~~(Math.random() * 256);
-
-      var offset = 0;
-      pair.server.req.on('data', function(chunk) {
-        for (var i = 0; i < chunk.length; i++) {
-          assert(i + offset < big.length);
-          assert.equal(big[i + offset], chunk[i]);
-        }
-        offset += i;
-      });
-
-      pair.server.req.on('close', function() {
-        assert(offset < big.length);
-        done();
-      });
-
-      pair.client.req.write(big.slice(0, big.length >> 1));
-      pair.client.req.write(big.slice(big.length >> 1));
-      pair.client.req.socket.destroy();
-    });
-
-    test('destroySoon in the middle', function(done) {
-      var big = new Buffer(2 * 1024 * 1024);
-      for (var i = 0; i < big.length; i++)
-        big[i] = ~~(Math.random() * 256);
-
-      var offset = 0;
-      pair.server.req.on('data', function(chunk) {
-        for (var i = 0; i < chunk.length; i++) {
-          assert(i + offset < big.length);
-          assert.equal(big[i + offset], chunk[i]);
-        }
-        offset += i;
-      });
-
-      pair.server.req.on('end', function() {
-        assert.equal(offset, big.length);
-        done();
-      });
-
-      pair.client.req.write(big.slice(0, big.length >> 1));
-      pair.client.req.write(big.slice(big.length >> 1));
-      pair.client.req.socket.destroySoon();
-    });
-
-    test('ending', function(done) {
-      var data = '';
-      pair.server.req.on('data', function(chunk) {
-        data += chunk;
-      });
-
-      pair.server.req.on('end', function() {
-        assert.equal(data, 'hello');
-        pair.server.res.end();
-        done();
-      });
-
-      pair.client.req.end('hello');
-    });
-
-    test('trailing headers from client', function(done) {
-      pair.server.req.once('trailers', function(headers) {
-        assert.equal(headers.wtf, 'yes');
-        assert.equal(pair.server.req.trailers.wtf, 'yes');
-        done();
-      });
-      pair.client.req.addTrailers({ wtf: 'yes' });
-    });
-
-    test('trailing headers from server', function(done) {
-      pair.client.res.once('trailers', function(headers) {
-        assert.equal(headers.wtf, 'yes');
-        assert.equal(pair.client.res.trailers.wtf, 'yes');
-        done();
-      });
-      pair.server.res.addTrailers({ wtf: 'yes' });
-    });
-
-    test('push stream', function(done) {
-      agent.once('push', function(req) {
-        var gotTrailers = false;
-        assert.equal(req.headers.wtf, 'true');
-
-        var chunks = '';
-        req.once('data', function(chunk) {
-          chunks += chunk;
-        });
-        req.once('trailers', function(trailers) {
-          assert.equal(trailers.ok, 'yes');
-          gotTrailers = true;
-        });
-        req.once('end', function() {
-          assert(gotTrailers);
-          assert.equal(req.trailers.ok, 'yes');
-          assert.equal(chunks, 'yes, wtf');
-          done();
-        });
-      });
-
-      pair.server.res.push('/wtf', { wtf: true }, function(err, stream) {
-        assert(!err);
-        stream.on('error', function(err) {
-          throw err;
-        });
-        stream.sendHeaders({ ok: 'yes' });
-        stream.end('yes, wtf');
-      });
-    });
-
-    test('push stream with compression', function(done) {
-      agent.once('push', function(req) {
-        req.once('data', function(chunk) {
-          assert.equal(chunk.toString(), 'yes, wtf');
-          done();
-        });
-      });
-      pair.server.res.push('/wtf', {
-        'Content-Encoding': 'gzip'
-      }, function(err, stream) {
-        assert(!err);
-        stream.on('error', function(err) {
-          throw err;
-        });
-        var gzip = zlib.createGzip();
-        gzip.on('data', function(data) {
-          stream.write(data);
-        });
-        gzip.on('end', function() {
-          stream.end();
-        });
-        gzip.end('yes, wtf');
-      });
-    });
-
-    test('push stream - big chunks', function(done) {
-      var count = 10;
-      var chunk = new Buffer(256 * 1024 - 7);
-      for (var i = 0; i < chunk.length; i++)
-        chunk[i] = ~~(Math.random() * 256);
-
-      agent.once('push', function(req) {
-        assert.equal(req.headers.wtf, 'true');
-        var offset = 0;
-        var total = 0;
-        req.on('data', function(data) {
-          for (var i = 0; i < data.length; i++) {
-            assert.equal(data[i],
-                         chunk[(offset + i) % chunk.length],
-                         'Mismatch at: ' + (offset + i));
-          }
-          offset = (offset + i) % chunk.length;
-          total += i;
-        });
-        req.once('end', function() {
-          assert.equal(total, count * chunk.length);
-          done();
-        });
-      });
-
-      pair.server.res.push('/wtf', { wtf: true }, function(err, stream) {
-        assert(!err);
-        stream.on('error', function(err) {
-          throw err;
-        });
-
-        function start(count) {
-          if (count === 1)
-            return stream.end(chunk);
-          stream.write(chunk);
-          setTimeout(function() {
-            start(count - 1);
-          }, 5);
-        }
-        start(count);
-      });
-    });
-
-    test('push stream - early close', function(done) {
-      agent.once('push', function(req) {
-        var chunks = '';
-        req.on('data', function(chunk) {
-          chunks += chunk;
-        });
-        req.once('end', function() {
-          assert.equal(chunks, 'yes, wtf');
-          done();
-        });
-      });
-      var stream = pair.server.res.push('/wtf', {});
-      pair.client.res.on('data', function() {});
-      pair.client.res.once('end', function() {
-        stream.end('yes, wtf');
-      });
-      pair.client.req.end();
-      pair.server.res.end();
-    });
-
-    test('timing out', function(done) {
-      var data = '';
-
-      pair.server.req.socket.setTimeout(300);
-      pair.client.req.on('error', function() {
-        done();
-      });
-    });
-
-    test('timing out after write', function(done) {
-      var data = '';
-      var chunks = 0;
-
-      pair.server.req.socket.setTimeout(150);
-      setTimeout(function() {
-        pair.server.res.write('ok1');
-        setTimeout(function() {
-          pair.server.res.write('ok2');
-        }, 100);
-      }, 100);
-
-      pair.client.res.on('data', function(chunk) {
-        chunk = chunk.toString();
-        assert(chunks === 0 && chunk === 'ok1' ||
-               chunks === 1 && chunk === 'ok2');
-        chunks++;
-      });
-
-      pair.client.req.on('error', function() {
-        assert.equal(chunks, 2);
-        done();
-      });
-    });
-
-    test('req[spdyVersion/streamID]', function(done) {
-      var data = '';
-      assert.equal(pair.server.req.spdyVersion, 3.1);
-      assert(pair.server.req.streamID > 0);
-
-      pair.server.req.resume();
-      pair.server.req.on('end', function() {
-        pair.server.res.end();
-        done();
-      });
-
-      pair.client.req.end();
-    });
-  }
-
-  test('it should not attempt to send empty arrays', function(done) {
-    var server = spdy.createServer(keys);
-    var agent;
-
-    server.on('request', function(req, res) {
-      setTimeout(function() {
-        res.end();
-        done();
-        server.close();
-        agent.close();
-      }, 100);
-    });
-
-    server.listen(PORT, function() {
-      agent = spdy.createAgent({
-        port: PORT,
-        rejectUnauthorized: false
-      }).on('error', function(err) {
-        done(err);
-      });
-
-      var body = new Buffer([1,2,3,4]);
-
-      var opts = {
-        method: 'POST',
-        headers: {
-          'Host': 'localhost',
-          'Content-Length': body.length
-        },
-        path: '/some-url',
-        agent: agent
-      };
-
-      var req = https.request(opts, function(res) {
-      }).on('error', function(err) {
-      });
-      req.end(body);
-    });
-  });
-});
--- a/testing/xpcshell/runxpcshelltests.py
+++ b/testing/xpcshell/runxpcshelltests.py
@@ -979,58 +979,54 @@ class XPCShellTests(object):
         """
           Simple wrapper to get the absolute path for a given directory name.
           On a remote system, we need to overload this to work on the remote filesystem.
         """
         return os.path.abspath(dirname)
 
     def trySetupNode(self):
         """
-          Run node for SPDY tests, if available, and updates mozinfo as appropriate.
+          Run node for HTTP/2 tests, if available, and updates mozinfo as appropriate.
         """
         nodeMozInfo = {'hasNode': False} # Assume the worst
         nodeBin = None
 
         # We try to find the node executable in the path given to us by the user in
         # the MOZ_NODE_PATH environment variable
         localPath = os.getenv('MOZ_NODE_PATH', None)
         if localPath and os.path.exists(localPath) and os.path.isfile(localPath):
             nodeBin = localPath
 
         if nodeBin:
             self.log.info('Found node at %s' % (nodeBin,))
 
             def startServer(name, serverJs):
                 if os.path.exists(serverJs):
-                    # OK, we found our SPDY server, let's try to get it running
+                    # OK, we found our server, let's try to get it running
                     self.log.info('Found %s at %s' % (name, serverJs))
                     try:
-                        # We pipe stdin to node because the spdy server will exit when its
+                        # We pipe stdin to node because the server will exit when its
                         # stdin reaches EOF
                         process = Popen([nodeBin, serverJs], stdin=PIPE, stdout=PIPE,
                                 stderr=PIPE, env=self.env, cwd=os.getcwd())
                         self.nodeProc[name] = process
 
                         # Check to make sure the server starts properly by waiting for it to
                         # tell us it's started
                         msg = process.stdout.readline()
                         if 'server listening' in msg:
                             nodeMozInfo['hasNode'] = True
-                            searchObj = re.search( r'SPDY server listening on port (.*)', msg, 0)
-                            if searchObj:
-                              self.env["MOZSPDY_PORT"] = searchObj.group(1)
                             searchObj = re.search( r'HTTP2 server listening on port (.*)', msg, 0)
                             if searchObj:
                               self.env["MOZHTTP2_PORT"] = searchObj.group(1)
                     except OSError, e:
                         # This occurs if the subprocess couldn't be started
                         self.log.error('Could not run %s server: %s' % (name, str(e)))
 
             myDir = os.path.split(os.path.abspath(__file__))[0]
-            startServer('moz-spdy', os.path.join(myDir, 'moz-spdy', 'moz-spdy.js'))
             startServer('moz-http2', os.path.join(myDir, 'moz-http2', 'moz-http2.js'))
         elif os.getenv('MOZ_ASSUME_NODE_RUNNING', None):
             self.log.info('Assuming required node servers are already running')
             nodeMozInfo['hasNode'] = True
 
         mozinfo.update(nodeMozInfo)
 
     def shutdownNode(self):
@@ -1232,17 +1228,17 @@ class XPCShellTests(object):
         # sections that defines a relative application directory for test runs. If
         # defined we pass 'grePath/$appDirKey' for the -a parameter of the xpcshell
         # test harness.
         appDirKey = None
         if "appname" in self.mozInfo:
             appDirKey = self.mozInfo["appname"] + "-appdir"
 
         # We have to do this before we build the test list so we know whether or
-        # not to run tests that depend on having the node spdy server
+        # not to run tests that depend on having the node http/2 server
         self.trySetupNode()
 
         pStdout, pStderr = self.getPipes()
 
         self.buildTestList(test_tags, testPaths)
         if self.singleFile:
             self.sequential = True