// Copyright 2014 The Go Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.

//go:build !(go1.27 && http2wrap)

package http2_test

import (
	"bytes"
	"compress/gzip"
	"compress/zlib"
	"context"
	"crypto/tls"
	"errors"
	"fmt"
	"io"
	"log"
	"math"
	"net"
	"net/http"
	"net/http/httptest"
	"os"
	"reflect"
	"runtime"
	"slices"
	"strconv"
	"strings"
	"sync"
	"testing"
	"testing/synctest"
	"time"

	. "golang.org/x/net/http2"
	"golang.org/x/net/http2/hpack"
)

func newTestServer(t testing.TB, handler http.HandlerFunc, opts ...interface{}) *httptest.Server {
	ts := httptest.NewUnstartedServer(handler)
	ts.EnableHTTP2 = true
	ts.Config.ErrorLog = log.New(twriter{t: t}, "", log.LstdFlags)
	h2server := new(Server)
	for _, opt := range opts {
		switch v := opt.(type) {
		case func(*httptest.Server):
			v(ts)
		case func(*http.Server):
			v(ts.Config)
		case func(*Server):
			v(h2server)
		default:
			t.Fatalf("unknown newTestServer option type %T", v)
		}
	}
	ConfigureServer(ts.Config, h2server)

	// ConfigureServer populates ts.Config.TLSConfig.
	// Copy it to ts.TLS as well.
	ts.TLS = ts.Config.TLSConfig

	// Go 1.22 changes the default minimum TLS version to TLS 1.2,
	// in order to properly test cases where we want to reject low
	// TLS versions, we need to explicitly configure the minimum
	// version here.
	ts.Config.TLSConfig.MinVersion = tls.VersionTLS10

	ts.StartTLS()
	t.Cleanup(func() {
		ts.CloseClientConnections()
		ts.Close()
	})

	return ts
}

// newServerTesterWithRealConn creates a test server listening on a localhost port.
// Mostly superseded by newServerTester, which creates a test server using a fake
// net.Conn and synthetic time. This function is still around because some benchmarks
// rely on it; new tests should use newServerTester.
func newServerTesterWithRealConn(t testing.TB, handler http.HandlerFunc, opts ...interface{}) *serverTester {
	ts := httptest.NewUnstartedServer(handler)
	t.Cleanup(ts.Close)

	tlsConfig := &tls.Config{
		InsecureSkipVerify: true,
		NextProtos:         []string{NextProtoTLS},
	}

	var framerReuseFrames bool
	h2server := new(Server)
	for _, opt := range opts {
		switch v := opt.(type) {
		case func(*tls.Config):
			v(tlsConfig)
		case func(*httptest.Server):
			v(ts)
		case func(*http.Server):
			v(ts.Config)
		case func(*Server):
			v(h2server)
		case serverTesterOpt:
			switch v {
			case optFramerReuseFrames:
				framerReuseFrames = true
			}
		case func(net.Conn, http.ConnState):
			ts.Config.ConnState = v
		default:
			t.Fatalf("unknown newServerTester option type %T", v)
		}
	}

	ConfigureServer(ts.Config, h2server)

	// Go 1.22 changes the default minimum TLS version to TLS 1.2,
	// in order to properly test cases where we want to reject low
	// TLS versions, we need to explicitly configure the minimum
	// version here.
	ts.Config.TLSConfig.MinVersion = tls.VersionTLS10

	st := &serverTester{
		t: t,
	}
	st.hpackEnc = hpack.NewEncoder(&st.headerBuf)

	ts.TLS = ts.Config.TLSConfig // the httptest.Server has its own copy of this TLS config
	if ts.Config.ErrorLog == nil {
		ts.Config.ErrorLog = log.New(io.MultiWriter(stderrv(), twriter{t: t, st: st}, &st.serverLogBuf), "", log.LstdFlags)
	}
	ts.StartTLS()

	if VerboseLogs {
		t.Logf("Running test server at: %s", ts.URL)
	}
	SetTestHookGetServerConn(t, func(v *ServerConn) {
		st.scMu.Lock()
		defer st.scMu.Unlock()
		st.sc = v
	})
	log.SetOutput(io.MultiWriter(stderrv(), twriter{t: t, st: st}))
	cc, err := tls.Dial("tcp", ts.Listener.Addr().String(), tlsConfig)
	if err != nil {
		t.Fatal(err)
	}
	st.cc = cc
	st.testConnFramer = testConnFramer{
		t:   t,
		fr:  NewFramer(st.cc, st.cc),
		dec: hpack.NewDecoder(InitialHeaderTableSize, nil),
	}
	if framerReuseFrames {
		st.fr.SetReuseFrames()
	}
	if !LogFrameReads() && !LogFrameWrites() {
		st.fr.TestSetDebugReadLoggerf(func(m string, v ...interface{}) {
			m = time.Now().Format("2006-01-02 15:04:05.999999999 ") + strings.TrimPrefix(m, "http2: ") + "\n"
			st.frameReadLogMu.Lock()
			fmt.Fprintf(&st.frameReadLogBuf, m, v...)
			st.frameReadLogMu.Unlock()
		})
		st.fr.TestSetDebugWriteLoggerf(func(m string, v ...interface{}) {
			m = time.Now().Format("2006-01-02 15:04:05.999999999 ") + strings.TrimPrefix(m, "http2: ") + "\n"
			st.frameWriteLogMu.Lock()
			fmt.Fprintf(&st.frameWriteLogBuf, m, v...)
			st.frameWriteLogMu.Unlock()
		})
	}
	return st
}

func (st *serverTester) streamExists(id uint32) bool {
	if st.sc == nil {
		st.t.Fatalf("serverTester has no ServerConn")
	}
	return st.sc.TestStreamExists(id)
}

func (st *serverTester) streamState(id uint32) StreamState {
	if st.sc == nil {
		st.t.Fatalf("serverTester has no ServerConn")
	}
	return st.sc.TestStreamState(id)
}

func (st *serverTester) wantConnFlowControlConsumed(consumed int32) {
	if got, want := st.sc.TestFlowControlConsumed(), consumed; got != want {
		st.t.Errorf("connection flow control consumed: %v, want %v", got, want)
	}
}

func TestServer(t *testing.T) { synctestTest(t, testServer) }
func testServer(t testing.TB) {
	gotReq := make(chan bool, 1)
	st := newServerTester(t, func(w http.ResponseWriter, r *http.Request) {
		w.Header().Set("Foo", "Bar")
		gotReq <- true
	})
	defer st.Close()

	st.greet()
	st.writeHeaders(HeadersFrameParam{
		StreamID:      1, // clients send odd numbers
		BlockFragment: st.encodeHeader(),
		EndStream:     true, // no DATA frames
		EndHeaders:    true,
	})

	<-gotReq
}

func TestServer_Request_Get(t *testing.T) { synctestTest(t, testServer_Request_Get) }
func testServer_Request_Get(t testing.TB) {
	testServerRequest(t, func(st *serverTester) {
		st.writeHeaders(HeadersFrameParam{
			StreamID:      1, // clients send odd numbers
			BlockFragment: st.encodeHeader("foo-bar", "some-value"),
			EndStream:     true, // no DATA frames
			EndHeaders:    true,
		})
	}, func(r *http.Request) {
		if r.Method != "GET" {
			t.Errorf("Method = %q; want GET", r.Method)
		}
		if r.URL.Path != "/" {
			t.Errorf("URL.Path = %q; want /", r.URL.Path)
		}
		if r.ContentLength != 0 {
			t.Errorf("ContentLength = %v; want 0", r.ContentLength)
		}
		if r.Close {
			t.Error("Close = true; want false")
		}
		if !strings.Contains(r.RemoteAddr, ":") {
			t.Errorf("RemoteAddr = %q; want something with a colon", r.RemoteAddr)
		}
		if r.Proto != "HTTP/2.0" || r.ProtoMajor != 2 || r.ProtoMinor != 0 {
			t.Errorf("Proto = %q Major=%v,Minor=%v; want HTTP/2.0", r.Proto, r.ProtoMajor, r.ProtoMinor)
		}
		wantHeader := http.Header{
			"Foo-Bar": []string{"some-value"},
		}
		if !reflect.DeepEqual(r.Header, wantHeader) {
			t.Errorf("Header = %#v; want %#v", r.Header, wantHeader)
		}
		if n, err := r.Body.Read([]byte(" ")); err != io.EOF || n != 0 {
			t.Errorf("Read = %d, %v; want 0, EOF", n, err)
		}
	})
}

func TestServer_Request_Get_PathSlashes(t *testing.T) {
	synctestTest(t, testServer_Request_Get_PathSlashes)
}
func testServer_Request_Get_PathSlashes(t testing.TB) {
	testServerRequest(t, func(st *serverTester) {
		st.writeHeaders(HeadersFrameParam{
			StreamID:      1, // clients send odd numbers
			BlockFragment: st.encodeHeader(":path", "/%2f/"),
			EndStream:     true, // no DATA frames
			EndHeaders:    true,
		})
	}, func(r *http.Request) {
		if r.RequestURI != "/%2f/" {
			t.Errorf("RequestURI = %q; want /%%2f/", r.RequestURI)
		}
		if r.URL.Path != "///" {
			t.Errorf("URL.Path = %q; want ///", r.URL.Path)
		}
	})
}

// TODO: add a test with EndStream=true on the HEADERS but setting a
// Content-Length anyway. Should we just omit it and force it to
// zero?

func TestServer_Request_Post_NoContentLength_EndStream(t *testing.T) {
	synctestTest(t, testServer_Request_Post_NoContentLength_EndStream)
}
func testServer_Request_Post_NoContentLength_EndStream(t testing.TB) {
	testServerRequest(t, func(st *serverTester) {
		st.writeHeaders(HeadersFrameParam{
			StreamID:      1, // clients send odd numbers
			BlockFragment: st.encodeHeader(":method", "POST"),
			EndStream:     true,
			EndHeaders:    true,
		})
	}, func(r *http.Request) {
		if r.Method != "POST" {
			t.Errorf("Method = %q; want POST", r.Method)
		}
		if r.ContentLength != 0 {
			t.Errorf("ContentLength = %v; want 0", r.ContentLength)
		}
		if n, err := r.Body.Read([]byte(" ")); err != io.EOF || n != 0 {
			t.Errorf("Read = %d, %v; want 0, EOF", n, err)
		}
	})
}

func TestServer_Request_Post_Body_ImmediateEOF(t *testing.T) {
	synctestTest(t, testServer_Request_Post_Body_ImmediateEOF)
}
func testServer_Request_Post_Body_ImmediateEOF(t testing.TB) {
	testBodyContents(t, -1, "", func(st *serverTester) {
		st.writeHeaders(HeadersFrameParam{
			StreamID:      1, // clients send odd numbers
			BlockFragment: st.encodeHeader(":method", "POST"),
			EndStream:     false, // to say DATA frames are coming
			EndHeaders:    true,
		})
		st.writeData(1, true, nil) // just kidding. empty body.
	})
}

func TestServer_Request_Post_Body_OneData(t *testing.T) {
	synctestTest(t, testServer_Request_Post_Body_OneData)
}
func testServer_Request_Post_Body_OneData(t testing.TB) {
	const content = "Some content"
	testBodyContents(t, -1, content, func(st *serverTester) {
		st.writeHeaders(HeadersFrameParam{
			StreamID:      1, // clients send odd numbers
			BlockFragment: st.encodeHeader(":method", "POST"),
			EndStream:     false, // to say DATA frames are coming
			EndHeaders:    true,
		})
		st.writeData(1, true, []byte(content))
	})
}

func TestServer_Request_Post_Body_TwoData(t *testing.T) {
	synctestTest(t, testServer_Request_Post_Body_TwoData)
}
func testServer_Request_Post_Body_TwoData(t testing.TB) {
	const content = "Some content"
	testBodyContents(t, -1, content, func(st *serverTester) {
		st.writeHeaders(HeadersFrameParam{
			StreamID:      1, // clients send odd numbers
			BlockFragment: st.encodeHeader(":method", "POST"),
			EndStream:     false, // to say DATA frames are coming
			EndHeaders:    true,
		})
		st.writeData(1, false, []byte(content[:5]))
		st.writeData(1, true, []byte(content[5:]))
	})
}

func TestServer_Request_Post_Body_ContentLength_Correct(t *testing.T) {
	synctestTest(t, testServer_Request_Post_Body_ContentLength_Correct)
}
func testServer_Request_Post_Body_ContentLength_Correct(t testing.TB) {
	const content = "Some content"
	testBodyContents(t, int64(len(content)), content, func(st *serverTester) {
		st.writeHeaders(HeadersFrameParam{
			StreamID: 1, // clients send odd numbers
			BlockFragment: st.encodeHeader(
				":method", "POST",
				"content-length", strconv.Itoa(len(content)),
			),
			EndStream:  false, // to say DATA frames are coming
			EndHeaders: true,
		})
		st.writeData(1, true, []byte(content))
	})
}

func TestServer_Request_Post_Body_ContentLength_TooLarge(t *testing.T) {
	synctestTest(t, testServer_Request_Post_Body_ContentLength_TooLarge)
}
func testServer_Request_Post_Body_ContentLength_TooLarge(t testing.TB) {
	testBodyContentsFail(t, 3, "request declared a Content-Length of 3 but only wrote 2 bytes",
		func(st *serverTester) {
			st.writeHeaders(HeadersFrameParam{
				StreamID: 1, // clients send odd numbers
				BlockFragment: st.encodeHeader(
					":method", "POST",
					"content-length", "3",
				),
				EndStream:  false, // to say DATA frames are coming
				EndHeaders: true,
			})
			st.writeData(1, true, []byte("12"))
		})
}

func TestServer_Request_Post_Body_ContentLength_TooSmall(t *testing.T) {
	synctestTest(t, testServer_Request_Post_Body_ContentLength_TooSmall)
}
func testServer_Request_Post_Body_ContentLength_TooSmall(t testing.TB) {
	testBodyContentsFail(t, 4, "sender tried to send more than declared Content-Length of 4 bytes",
		func(st *serverTester) {
			st.writeHeaders(HeadersFrameParam{
				StreamID: 1, // clients send odd numbers
				BlockFragment: st.encodeHeader(
					":method", "POST",
					"content-length", "4",
				),
				EndStream:  false, // to say DATA frames are coming
				EndHeaders: true,
			})
			st.writeData(1, true, []byte("12345"))
			// Return flow control bytes back, since the data handler closed
			// the stream.
			st.wantRSTStream(1, ErrCodeProtocol)
			st.wantConnFlowControlConsumed(0)
		})
}

func testBodyContents(t testing.TB, wantContentLength int64, wantBody string, write func(st *serverTester)) {
	testServerRequest(t, write, func(r *http.Request) {
		if r.Method != "POST" {
			t.Errorf("Method = %q; want POST", r.Method)
		}
		if r.ContentLength != wantContentLength {
			t.Errorf("ContentLength = %v; want %d", r.ContentLength, wantContentLength)
		}
		all, err := io.ReadAll(r.Body)
		if err != nil {
			t.Fatal(err)
		}
		if string(all) != wantBody {
			t.Errorf("Read = %q; want %q", all, wantBody)
		}
		if err := r.Body.Close(); err != nil {
			t.Fatalf("Close: %v", err)
		}
	})
}

func testBodyContentsFail(t testing.TB, wantContentLength int64, wantReadError string, write func(st *serverTester)) {
	testServerRequest(t, write, func(r *http.Request) {
		if r.Method != "POST" {
			t.Errorf("Method = %q; want POST", r.Method)
		}
		if r.ContentLength != wantContentLength {
			t.Errorf("ContentLength = %v; want %d", r.ContentLength, wantContentLength)
		}
		all, err := io.ReadAll(r.Body)
		if err == nil {
			t.Fatalf("expected an error (%q) reading from the body. Successfully read %q instead.",
				wantReadError, all)
		}
		if !strings.Contains(err.Error(), wantReadError) {
			t.Fatalf("Body.Read = %v; want substring %q", err, wantReadError)
		}
		if err := r.Body.Close(); err != nil {
			t.Fatalf("Close: %v", err)
		}
	})
}

// Using a Host header, instead of :authority
func TestServer_Request_Get_Host(t *testing.T) { synctestTest(t, testServer_Request_Get_Host) }
func testServer_Request_Get_Host(t testing.TB) {
	const host = "example.com"
	testServerRequest(t, func(st *serverTester) {
		st.writeHeaders(HeadersFrameParam{
			StreamID:      1, // clients send odd numbers
			BlockFragment: st.encodeHeader(":authority", "", "host", host),
			EndStream:     true,
			EndHeaders:    true,
		})
	}, func(r *http.Request) {
		if r.Host != host {
			t.Errorf("Host = %q; want %q", r.Host, host)
		}
	})
}

// Using an :authority pseudo-header, instead of Host
func TestServer_Request_Get_Authority(t *testing.T) {
	synctestTest(t, testServer_Request_Get_Authority)
}
func testServer_Request_Get_Authority(t testing.TB) {
	const host = "example.com"
	testServerRequest(t, func(st *serverTester) {
		st.writeHeaders(HeadersFrameParam{
			StreamID:      1, // clients send odd numbers
			BlockFragment: st.encodeHeader(":authority", host),
			EndStream:     true,
			EndHeaders:    true,
		})
	}, func(r *http.Request) {
		if r.Host != host {
			t.Errorf("Host = %q; want %q", r.Host, host)
		}
	})
}

func TestServer_Request_WithContinuation(t *testing.T) {
	synctestTest(t, testServer_Request_WithContinuation)
}
func testServer_Request_WithContinuation(t testing.TB) {
	wantHeader := http.Header{
		"Foo-One":   []string{"value-one"},
		"Foo-Two":   []string{"value-two"},
		"Foo-Three": []string{"value-three"},
	}
	testServerRequest(t, func(st *serverTester) {
		fullHeaders := st.encodeHeader(
			"foo-one", "value-one",
			"foo-two", "value-two",
			"foo-three", "value-three",
		)
		remain := fullHeaders
		chunks := 0
		for len(remain) > 0 {
			const maxChunkSize = 5
			chunk := remain
			if len(chunk) > maxChunkSize {
				chunk = chunk[:maxChunkSize]
			}
			remain = remain[len(chunk):]

			if chunks == 0 {
				st.writeHeaders(HeadersFrameParam{
					StreamID:      1, // clients send odd numbers
					BlockFragment: chunk,
					EndStream:     true,  // no DATA frames
					EndHeaders:    false, // we'll have continuation frames
				})
			} else {
				err := st.fr.WriteContinuation(1, len(remain) == 0, chunk)
				if err != nil {
					t.Fatal(err)
				}
			}
			chunks++
		}
		if chunks < 2 {
			t.Fatal("too few chunks")
		}
	}, func(r *http.Request) {
		if !reflect.DeepEqual(r.Header, wantHeader) {
			t.Errorf("Header = %#v; want %#v", r.Header, wantHeader)
		}
	})
}

// Concatenated cookie headers. ("8.1.2.5 Compressing the Cookie Header Field")
func TestServer_Request_CookieConcat(t *testing.T) { synctestTest(t, testServer_Request_CookieConcat) }
func testServer_Request_CookieConcat(t testing.TB) {
	const host = "example.com"
	testServerRequest(t, func(st *serverTester) {
		st.bodylessReq1(
			":authority", host,
			"cookie", "a=b",
			"cookie", "c=d",
			"cookie", "e=f",
		)
	}, func(r *http.Request) {
		const want = "a=b; c=d; e=f"
		if got := r.Header.Get("Cookie"); got != want {
			t.Errorf("Cookie = %q; want %q", got, want)
		}
	})
}

func TestServer_Request_Reject_CapitalHeader(t *testing.T) {
	testRejectRequest(t, func(st *serverTester) { st.bodylessReq1("UPPER", "v") })
}

func TestServer_Request_Reject_HeaderFieldNameColon(t *testing.T) {
	testRejectRequest(t, func(st *serverTester) { st.bodylessReq1("has:colon", "v") })
}

func TestServer_Request_Reject_HeaderFieldNameNULL(t *testing.T) {
	testRejectRequest(t, func(st *serverTester) { st.bodylessReq1("has\x00null", "v") })
}

func TestServer_Request_Reject_HeaderFieldNameEmpty(t *testing.T) {
	testRejectRequest(t, func(st *serverTester) { st.bodylessReq1("", "v") })
}

func TestServer_Request_Reject_HeaderFieldValueNewline(t *testing.T) {
	testRejectRequest(t, func(st *serverTester) { st.bodylessReq1("foo", "has\nnewline") })
}

func TestServer_Request_Reject_HeaderFieldValueCR(t *testing.T) {
	testRejectRequest(t, func(st *serverTester) { st.bodylessReq1("foo", "has\rcarriage") })
}

func TestServer_Request_Reject_HeaderFieldValueDEL(t *testing.T) {
	testRejectRequest(t, func(st *serverTester) { st.bodylessReq1("foo", "has\x7fdel") })
}

func TestServer_Request_Reject_Pseudo_Missing_method(t *testing.T) {
	testRejectRequest(t, func(st *serverTester) { st.bodylessReq1(":method", "") })
}

func TestServer_Request_Reject_Pseudo_ExactlyOne(t *testing.T) {
	// 8.1.2.3 Request Pseudo-Header Fields
	// "All HTTP/2 requests MUST include exactly one valid value" ...
	testRejectRequest(t, func(st *serverTester) {
		st.addLogFilter("duplicate pseudo-header")
		st.bodylessReq1(":method", "GET", ":method", "POST")
	})
}

func TestServer_Request_Reject_Pseudo_AfterRegular(t *testing.T) {
	// 8.1.2.3 Request Pseudo-Header Fields
	// "All pseudo-header fields MUST appear in the header block
	// before regular header fields. Any request or response that
	// contains a pseudo-header field that appears in a header
	// block after a regular header field MUST be treated as
	// malformed (Section 8.1.2.6)."
	testRejectRequest(t, func(st *serverTester) {
		st.addLogFilter("pseudo-header after regular header")
		var buf bytes.Buffer
		enc := hpack.NewEncoder(&buf)
		enc.WriteField(hpack.HeaderField{Name: ":method", Value: "GET"})
		enc.WriteField(hpack.HeaderField{Name: "regular", Value: "foobar"})
		enc.WriteField(hpack.HeaderField{Name: ":path", Value: "/"})
		enc.WriteField(hpack.HeaderField{Name: ":scheme", Value: "https"})
		st.writeHeaders(HeadersFrameParam{
			StreamID:      1, // clients send odd numbers
			BlockFragment: buf.Bytes(),
			EndStream:     true,
			EndHeaders:    true,
		})
	})
}

func TestServer_Request_Reject_Pseudo_Missing_path(t *testing.T) {
	testRejectRequest(t, func(st *serverTester) { st.bodylessReq1(":path", "") })
}

func TestServer_Request_Reject_Pseudo_Missing_scheme(t *testing.T) {
	testRejectRequest(t, func(st *serverTester) { st.bodylessReq1(":scheme", "") })
}

func TestServer_Request_Reject_Pseudo_scheme_invalid(t *testing.T) {
	testRejectRequest(t, func(st *serverTester) { st.bodylessReq1(":scheme", "bogus") })
}

func TestServer_Request_Reject_Pseudo_Unknown(t *testing.T) {
	testRejectRequest(t, func(st *serverTester) {
		st.addLogFilter(`invalid pseudo-header ":unknown_thing"`)
		st.bodylessReq1(":unknown_thing", "")
	})
}

func TestServer_Request_Reject_Authority_Userinfo(t *testing.T) {
	// "':authority' MUST NOT include the deprecated userinfo subcomponent
	// for "http" or "https" schemed URIs."
	// https://www.rfc-editor.org/rfc/rfc9113.html#section-8.3.1-2.3.8
	testRejectRequest(t, func(st *serverTester) {
		var buf bytes.Buffer
		enc := hpack.NewEncoder(&buf)
		enc.WriteField(hpack.HeaderField{Name: ":authority", Value: "userinfo@example.tld"})
		enc.WriteField(hpack.HeaderField{Name: ":method", Value: "GET"})
		enc.WriteField(hpack.HeaderField{Name: ":path", Value: "/"})
		enc.WriteField(hpack.HeaderField{Name: ":scheme", Value: "https"})
		st.writeHeaders(HeadersFrameParam{
			StreamID:      1, // clients send odd numbers
			BlockFragment: buf.Bytes(),
			EndStream:     true,
			EndHeaders:    true,
		})
	})
}

func testRejectRequest(t *testing.T, send func(*serverTester)) {
	synctestTest(t, func(t testing.TB) {
		st := newServerTester(t, func(w http.ResponseWriter, r *http.Request) {
			t.Error("server request made it to handler; should've been rejected")
		})
		defer st.Close()

		st.greet()
		send(st)
		st.wantRSTStream(1, ErrCodeProtocol)
	})
}

func newServerTesterForError(t testing.TB) *serverTester {
	t.Helper()
	st := newServerTester(t, func(w http.ResponseWriter, r *http.Request) {
		t.Error("server request made it to handler; should've been rejected")
	}, optQuiet)
	st.greet()
	return st
}

// Section 5.1, on idle connections: "Receiving any frame other than
// HEADERS or PRIORITY on a stream in this state MUST be treated as a
// connection error (Section 5.4.1) of type PROTOCOL_ERROR."
func TestRejectFrameOnIdle_WindowUpdate(t *testing.T) {
	synctestTest(t, testRejectFrameOnIdle_WindowUpdate)
}
func testRejectFrameOnIdle_WindowUpdate(t testing.TB) {
	st := newServerTesterForError(t)
	st.fr.WriteWindowUpdate(123, 456)
	st.wantGoAway(123, ErrCodeProtocol)
}
func TestRejectFrameOnIdle_Data(t *testing.T) { synctestTest(t, testRejectFrameOnIdle_Data) }
func testRejectFrameOnIdle_Data(t testing.TB) {
	st := newServerTesterForError(t)
	st.fr.WriteData(123, true, nil)
	st.wantGoAway(123, ErrCodeProtocol)
}
func TestRejectFrameOnIdle_RSTStream(t *testing.T) { synctestTest(t, testRejectFrameOnIdle_RSTStream) }
func testRejectFrameOnIdle_RSTStream(t testing.TB) {
	st := newServerTesterForError(t)
	st.fr.WriteRSTStream(123, ErrCodeCancel)
	st.wantGoAway(123, ErrCodeProtocol)
}

func TestServer_Request_Connect(t *testing.T) { synctestTest(t, testServer_Request_Connect) }
func testServer_Request_Connect(t testing.TB) {
	testServerRequest(t, func(st *serverTester) {
		st.writeHeaders(HeadersFrameParam{
			StreamID: 1,
			BlockFragment: st.encodeHeaderRaw(
				":method", "CONNECT",
				":authority", "example.com:123",
			),
			EndStream:  true,
			EndHeaders: true,
		})
	}, func(r *http.Request) {
		if g, w := r.Method, "CONNECT"; g != w {
			t.Errorf("Method = %q; want %q", g, w)
		}
		if g, w := r.RequestURI, "example.com:123"; g != w {
			t.Errorf("RequestURI = %q; want %q", g, w)
		}
		if g, w := r.URL.Host, "example.com:123"; g != w {
			t.Errorf("URL.Host = %q; want %q", g, w)
		}
	})
}

func TestServer_Request_Connect_InvalidPath(t *testing.T) {
	synctestTest(t, testServer_Request_Connect_InvalidPath)
}
func testServer_Request_Connect_InvalidPath(t testing.TB) {
	testServerRejectsStream(t, ErrCodeProtocol, func(st *serverTester) {
		st.writeHeaders(HeadersFrameParam{
			StreamID: 1,
			BlockFragment: st.encodeHeaderRaw(
				":method", "CONNECT",
				":authority", "example.com:123",
				":path", "/bogus",
			),
			EndStream:  true,
			EndHeaders: true,
		})
	})
}

func TestServer_Request_Connect_InvalidScheme(t *testing.T) {
	synctestTest(t, testServer_Request_Connect_InvalidScheme)
}
func testServer_Request_Connect_InvalidScheme(t testing.TB) {
	testServerRejectsStream(t, ErrCodeProtocol, func(st *serverTester) {
		st.writeHeaders(HeadersFrameParam{
			StreamID: 1,
			BlockFragment: st.encodeHeaderRaw(
				":method", "CONNECT",
				":authority", "example.com:123",
				":scheme", "https",
			),
			EndStream:  true,
			EndHeaders: true,
		})
	})
}

func TestServer_Ping(t *testing.T) { synctestTest(t, testServer_Ping) }
func testServer_Ping(t testing.TB) {
	st := newServerTester(t, nil)
	defer st.Close()
	st.greet()

	// Server should ignore this one, since it has ACK set.
	ackPingData := [8]byte{1, 2, 4, 8, 16, 32, 64, 128}
	if err := st.fr.WritePing(true, ackPingData); err != nil {
		t.Fatal(err)
	}

	// But the server should reply to this one, since ACK is false.
	pingData := [8]byte{1, 2, 3, 4, 5, 6, 7, 8}
	if err := st.fr.WritePing(false, pingData); err != nil {
		t.Fatal(err)
	}

	pf := readFrame[*PingFrame](t, st)
	if !pf.Flags.Has(FlagPingAck) {
		t.Error("response ping doesn't have ACK set")
	}
	if pf.Data != pingData {
		t.Errorf("response ping has data %q; want %q", pf.Data, pingData)
	}
}

type filterListener struct {
	net.Listener
	accept func(conn net.Conn) (net.Conn, error)
}

func (l *filterListener) Accept() (net.Conn, error) {
	c, err := l.Listener.Accept()
	if err != nil {
		return nil, err
	}
	return l.accept(c)
}

func TestServer_MaxQueuedControlFrames(t *testing.T) {
	synctestTest(t, testServer_MaxQueuedControlFrames)
}
func testServer_MaxQueuedControlFrames(t testing.TB) {
	// Goroutine debugging makes this test very slow.
	DisableGoroutineTracking(t)

	st := newServerTester(t, nil)
	st.greet()

	st.cc.(*synctestNetConn).SetReadBufferSize(0) // all writes block
	st.cc.(*synctestNetConn).autoWait = false     // don't sync after every write

	// Send maxQueuedControlFrames pings, plus a few extra
	// to account for ones that enter the server's write buffer.
	const extraPings = 2
	for i := 0; i < MaxQueuedControlFrames+extraPings; i++ {
		pingData := [8]byte{1, 2, 3, 4, 5, 6, 7, 8}
		st.fr.WritePing(false, pingData)
	}
	synctest.Wait()

	// Unblock the server.
	// It should have closed the connection after exceeding the control frame limit.
	st.cc.(*synctestNetConn).SetReadBufferSize(math.MaxInt)

	st.advance(GoAwayTimeout)
	// Some frames may have persisted in the server's buffers.
	for i := 0; i < 10; i++ {
		if st.readFrame() == nil {
			break
		}
	}
	st.wantClosed()
}

func TestServer_RejectsLargeFrames(t *testing.T) { synctestTest(t, testServer_RejectsLargeFrames) }
func testServer_RejectsLargeFrames(t testing.TB) {
	if runtime.GOOS == "windows" || runtime.GOOS == "plan9" || runtime.GOOS == "zos" {
		t.Skip("see golang.org/issue/13434, golang.org/issue/37321")
	}
	st := newServerTester(t, nil)
	defer st.Close()
	st.greet()

	// Write too large of a frame (too large by one byte)
	// We ignore the return value because it's expected that the server
	// will only read the first 9 bytes (the headre) and then disconnect.
	st.fr.WriteRawFrame(0xff, 0, 0, make([]byte, DefaultMaxReadFrameSize+1))

	st.wantGoAway(0, ErrCodeFrameSize)
	st.advance(GoAwayTimeout)
	st.wantClosed()
}

func TestServer_Handler_Sends_WindowUpdate(t *testing.T) {
	synctestTest(t, testServer_Handler_Sends_WindowUpdate)
}
func testServer_Handler_Sends_WindowUpdate(t testing.TB) {
	// Need to set this to at least twice the initial window size,
	// or st.greet gets stuck waiting for a WINDOW_UPDATE.
	//
	// This also needs to be less than MAX_FRAME_SIZE.
	const windowSize = 65535 * 2
	st := newServerTester(t, nil, func(s *Server) {
		s.MaxUploadBufferPerConnection = windowSize
		s.MaxUploadBufferPerStream = windowSize
	})
	defer st.Close()

	st.greet()
	st.writeHeaders(HeadersFrameParam{
		StreamID:      1, // clients send odd numbers
		BlockFragment: st.encodeHeader(":method", "POST"),
		EndStream:     false, // data coming
		EndHeaders:    true,
	})
	call := st.nextHandlerCall()

	// Write less than half the max window of data and consume it.
	// The server doesn't return flow control yet, buffering the 1024 bytes to
	// combine with a future update.
	data := make([]byte, windowSize)
	st.writeData(1, false, data[:1024])
	call.do(readBodyHandler(t, string(data[:1024])))

	// Write up to the window limit.
	// The server returns the buffered credit.
	st.writeData(1, false, data[1024:])
	st.wantWindowUpdate(0, 1024)
	st.wantWindowUpdate(1, 1024)

	// The handler consumes the data and the server returns credit.
	call.do(readBodyHandler(t, string(data[1024:])))
	st.wantWindowUpdate(0, windowSize-1024)
	st.wantWindowUpdate(1, windowSize-1024)
}

// the version of the TestServer_Handler_Sends_WindowUpdate with padding.
// See golang.org/issue/16556
func TestServer_Handler_Sends_WindowUpdate_Padding(t *testing.T) {
	synctestTest(t, testServer_Handler_Sends_WindowUpdate_Padding)
}
func testServer_Handler_Sends_WindowUpdate_Padding(t testing.TB) {
	const windowSize = 65535 * 2
	st := newServerTester(t, nil, func(s *Server) {
		s.MaxUploadBufferPerConnection = windowSize
		s.MaxUploadBufferPerStream = windowSize
	})
	defer st.Close()

	st.greet()
	st.writeHeaders(HeadersFrameParam{
		StreamID:      1,
		BlockFragment: st.encodeHeader(":method", "POST"),
		EndStream:     false,
		EndHeaders:    true,
	})
	call := st.nextHandlerCall()

	// Write half a window of data, with some padding.
	// The server doesn't return the padding yet, buffering the 5 bytes to combine
	// with a future update.
	data := make([]byte, windowSize/2)
	pad := make([]byte, 4)
	st.writeDataPadded(1, false, data, pad)

	// The handler consumes the body.
	// The server returns flow control for the body and padding
	// (4 bytes of padding + 1 byte of length).
	call.do(readBodyHandler(t, string(data)))
	st.wantWindowUpdate(0, uint32(len(data)+1+len(pad)))
	st.wantWindowUpdate(1, uint32(len(data)+1+len(pad)))
}

func TestServer_Send_GoAway_After_Bogus_WindowUpdate(t *testing.T) {
	synctestTest(t, testServer_Send_GoAway_After_Bogus_WindowUpdate)
}
func testServer_Send_GoAway_After_Bogus_WindowUpdate(t testing.TB) {
	st := newServerTester(t, nil)
	defer st.Close()
	st.greet()
	if err := st.fr.WriteWindowUpdate(0, 1<<31-1); err != nil {
		t.Fatal(err)
	}
	st.wantGoAway(0, ErrCodeFlowControl)
}

func TestServer_Send_RstStream_After_Bogus_WindowUpdate(t *testing.T) {
	synctestTest(t, testServer_Send_RstStream_After_Bogus_WindowUpdate)
}
func testServer_Send_RstStream_After_Bogus_WindowUpdate(t testing.TB) {
	inHandler := make(chan bool)
	blockHandler := make(chan bool)
	st := newServerTester(t, func(w http.ResponseWriter, r *http.Request) {
		inHandler <- true
		<-blockHandler
	})
	defer st.Close()
	defer close(blockHandler)
	st.greet()
	st.writeHeaders(HeadersFrameParam{
		StreamID:      1,
		BlockFragment: st.encodeHeader(":method", "POST"),
		EndStream:     false, // keep it open
		EndHeaders:    true,
	})
	<-inHandler
	// Send a bogus window update:
	if err := st.fr.WriteWindowUpdate(1, 1<<31-1); err != nil {
		t.Fatal(err)
	}
	st.wantRSTStream(1, ErrCodeFlowControl)
}

// testServerPostUnblock sends a hanging POST with unsent data to handler,
// then runs fn once in the handler, and verifies that the error returned from
// handler is acceptable. It fails if takes over 5 seconds for handler to exit.
func testServerPostUnblock(t testing.TB,
	handler func(http.ResponseWriter, *http.Request) error,
	fn func(*serverTester),
	checkErr func(error),
	otherHeaders ...string) {
	inHandler := make(chan bool)
	errc := make(chan error, 1)
	st := newServerTester(t, func(w http.ResponseWriter, r *http.Request) {
		inHandler <- true
		errc <- handler(w, r)
	})
	defer st.Close()
	st.greet()
	st.writeHeaders(HeadersFrameParam{
		StreamID:      1,
		BlockFragment: st.encodeHeader(append([]string{":method", "POST"}, otherHeaders...)...),
		EndStream:     false, // keep it open
		EndHeaders:    true,
	})
	<-inHandler
	fn(st)
	err := <-errc
	if checkErr != nil {
		checkErr(err)
	}
}

func TestServer_RSTStream_Unblocks_Read(t *testing.T) {
	synctestTest(t, testServer_RSTStream_Unblocks_Read)
}
func testServer_RSTStream_Unblocks_Read(t testing.TB) {
	testServerPostUnblock(t,
		func(w http.ResponseWriter, r *http.Request) (err error) {
			_, err = r.Body.Read(make([]byte, 1))
			return
		},
		func(st *serverTester) {
			if err := st.fr.WriteRSTStream(1, ErrCodeCancel); err != nil {
				t.Fatal(err)
			}
		},
		func(err error) {
			want := StreamError{StreamID: 0x1, Code: 0x8}
			if !reflect.DeepEqual(err, want) {
				t.Errorf("Read error = %v; want %v", err, want)
			}
		},
	)
}

func TestServer_RSTStream_Unblocks_Header_Write(t *testing.T) {
	// Run this test a bunch, because it doesn't always
	// deadlock. But with a bunch, it did.
	n := 50
	if testing.Short() {
		n = 5
	}
	for i := 0; i < n; i++ {
		synctestTest(t, testServer_RSTStream_Unblocks_Header_Write)
	}
}

func testServer_RSTStream_Unblocks_Header_Write(t testing.TB) {
	inHandler := make(chan bool, 1)
	unblockHandler := make(chan bool, 1)
	headerWritten := make(chan bool, 1)
	wroteRST := make(chan bool, 1)

	st := newServerTester(t, func(w http.ResponseWriter, r *http.Request) {
		inHandler <- true
		<-wroteRST
		w.Header().Set("foo", "bar")
		w.WriteHeader(200)
		w.(http.Flusher).Flush()
		headerWritten <- true
		<-unblockHandler
	})
	defer st.Close()

	st.greet()
	st.writeHeaders(HeadersFrameParam{
		StreamID:      1,
		BlockFragment: st.encodeHeader(":method", "POST"),
		EndStream:     false, // keep it open
		EndHeaders:    true,
	})
	<-inHandler
	if err := st.fr.WriteRSTStream(1, ErrCodeCancel); err != nil {
		t.Fatal(err)
	}
	wroteRST <- true
	synctest.Wait()
	<-headerWritten
	unblockHandler <- true
}

func TestServer_DeadConn_Unblocks_Read(t *testing.T) {
	synctestTest(t, testServer_DeadConn_Unblocks_Read)
}
func testServer_DeadConn_Unblocks_Read(t testing.TB) {
	testServerPostUnblock(t,
		func(w http.ResponseWriter, r *http.Request) (err error) {
			_, err = r.Body.Read(make([]byte, 1))
			return
		},
		func(st *serverTester) { st.cc.Close() },
		func(err error) {
			if err == nil {
				t.Error("unexpected nil error from Request.Body.Read")
			}
		},
	)
}

var blockUntilClosed = func(w http.ResponseWriter, r *http.Request) error {
	<-w.(http.CloseNotifier).CloseNotify()
	return nil
}

func TestServer_CloseNotify_After_RSTStream(t *testing.T) {
	synctestTest(t, testServer_CloseNotify_After_RSTStream)
}
func testServer_CloseNotify_After_RSTStream(t testing.TB) {
	testServerPostUnblock(t, blockUntilClosed, func(st *serverTester) {
		if err := st.fr.WriteRSTStream(1, ErrCodeCancel); err != nil {
			t.Fatal(err)
		}
	}, nil)
}

func TestServer_CloseNotify_After_ConnClose(t *testing.T) {
	synctestTest(t, testServer_CloseNotify_After_ConnClose)
}
func testServer_CloseNotify_After_ConnClose(t testing.TB) {
	testServerPostUnblock(t, blockUntilClosed, func(st *serverTester) { st.cc.Close() }, nil)
}

// that CloseNotify unblocks after a stream error due to the client's
// problem that's unrelated to them explicitly canceling it (which is
// TestServer_CloseNotify_After_RSTStream above)
func TestServer_CloseNotify_After_StreamError(t *testing.T) {
	synctestTest(t, testServer_CloseNotify_After_StreamError)
}
func testServer_CloseNotify_After_StreamError(t testing.TB) {
	testServerPostUnblock(t, blockUntilClosed, func(st *serverTester) {
		// data longer than declared Content-Length => stream error
		st.writeData(1, true, []byte("1234"))
	}, nil, "content-length", "3")
}

func TestServer_StateTransitions(t *testing.T) { synctestTest(t, testServer_StateTransitions) }
func testServer_StateTransitions(t testing.TB) {
	var st *serverTester
	inHandler := make(chan bool)
	writeData := make(chan bool)
	leaveHandler := make(chan bool)
	st = newServerTester(t, func(w http.ResponseWriter, r *http.Request) {
		inHandler <- true
		if !st.streamExists(1) {
			t.Errorf("stream 1 does not exist in handler")
		}
		if got, want := st.streamState(1), StateOpen; got != want {
			t.Errorf("in handler, state is %v; want %v", got, want)
		}
		writeData <- true
		if n, err := r.Body.Read(make([]byte, 1)); n != 0 || err != io.EOF {
			t.Errorf("body read = %d, %v; want 0, EOF", n, err)
		}
		if got, want := st.streamState(1), StateHalfClosedRemote; got != want {
			t.Errorf("in handler, state is %v; want %v", got, want)
		}

		<-leaveHandler
	})
	st.greet()
	if st.streamExists(1) {
		t.Fatal("stream 1 should be empty")
	}
	if got := st.streamState(1); got != StateIdle {
		t.Fatalf("stream 1 should be idle; got %v", got)
	}

	st.writeHeaders(HeadersFrameParam{
		StreamID:      1,
		BlockFragment: st.encodeHeader(":method", "POST"),
		EndStream:     false, // keep it open
		EndHeaders:    true,
	})
	<-inHandler
	<-writeData
	st.writeData(1, true, nil)

	leaveHandler <- true
	st.wantHeaders(wantHeader{
		streamID:  1,
		endStream: true,
	})

	if got, want := st.streamState(1), StateClosed; got != want {
		t.Errorf("at end, state is %v; want %v", got, want)
	}
	if st.streamExists(1) {
		t.Fatal("at end, stream 1 should be gone")
	}
}

// test HEADERS w/o EndHeaders + another HEADERS (should get rejected)
func TestServer_Rejects_HeadersNoEnd_Then_Headers(t *testing.T) {
	synctestTest(t, testServer_Rejects_HeadersNoEnd_Then_Headers)
}
func testServer_Rejects_HeadersNoEnd_Then_Headers(t testing.TB) {
	st := newServerTesterForError(t)
	st.writeHeaders(HeadersFrameParam{
		StreamID:      1,
		BlockFragment: st.encodeHeader(),
		EndStream:     true,
		EndHeaders:    false,
	})
	st.writeHeaders(HeadersFrameParam{ // Not a continuation.
		StreamID:      3, // different stream.
		BlockFragment: st.encodeHeader(),
		EndStream:     true,
		EndHeaders:    true,
	})
	st.wantGoAway(0, ErrCodeProtocol)
}

// test HEADERS w/o EndHeaders + PING (should get rejected)
func TestServer_Rejects_HeadersNoEnd_Then_Ping(t *testing.T) {
	synctestTest(t, testServer_Rejects_HeadersNoEnd_Then_Ping)
}
func testServer_Rejects_HeadersNoEnd_Then_Ping(t testing.TB) {
	st := newServerTesterForError(t)
	st.writeHeaders(HeadersFrameParam{
		StreamID:      1,
		BlockFragment: st.encodeHeader(),
		EndStream:     true,
		EndHeaders:    false,
	})
	if err := st.fr.WritePing(false, [8]byte{}); err != nil {
		t.Fatal(err)
	}
	st.wantGoAway(0, ErrCodeProtocol)
}

// test HEADERS w/ EndHeaders + a continuation HEADERS (should get rejected)
func TestServer_Rejects_HeadersEnd_Then_Continuation(t *testing.T) {
	synctestTest(t, testServer_Rejects_HeadersEnd_Then_Continuation)
}
func testServer_Rejects_HeadersEnd_Then_Continuation(t testing.TB) {
	st := newServerTester(t, func(w http.ResponseWriter, r *http.Request) {}, optQuiet)
	st.greet()
	st.writeHeaders(HeadersFrameParam{
		StreamID:      1,
		BlockFragment: st.encodeHeader(),
		EndStream:     true,
		EndHeaders:    true,
	})
	st.wantHeaders(wantHeader{
		streamID:  1,
		endStream: true,
	})
	if err := st.fr.WriteContinuation(1, true, EncodeHeaderRaw(t, "foo", "bar")); err != nil {
		t.Fatal(err)
	}
	st.wantGoAway(1, ErrCodeProtocol)
}

// test HEADERS w/o EndHeaders + a continuation HEADERS on wrong stream ID
func TestServer_Rejects_HeadersNoEnd_Then_ContinuationWrongStream(t *testing.T) {
	synctestTest(t, testServer_Rejects_HeadersNoEnd_Then_ContinuationWrongStream)
}
func testServer_Rejects_HeadersNoEnd_Then_ContinuationWrongStream(t testing.TB) {
	st := newServerTesterForError(t)
	st.writeHeaders(HeadersFrameParam{
		StreamID:      1,
		BlockFragment: st.encodeHeader(),
		EndStream:     true,
		EndHeaders:    false,
	})
	if err := st.fr.WriteContinuation(3, true, EncodeHeaderRaw(t, "foo", "bar")); err != nil {
		t.Fatal(err)
	}
	st.wantGoAway(0, ErrCodeProtocol)
}

// No HEADERS on stream 0.
func TestServer_Rejects_Headers0(t *testing.T) { synctestTest(t, testServer_Rejects_Headers0) }
func testServer_Rejects_Headers0(t testing.TB) {
	st := newServerTesterForError(t)
	st.fr.AllowIllegalWrites = true
	st.writeHeaders(HeadersFrameParam{
		StreamID:      0,
		BlockFragment: st.encodeHeader(),
		EndStream:     true,
		EndHeaders:    true,
	})
	st.wantGoAway(0, ErrCodeProtocol)
}

// No CONTINUATION on stream 0.
func TestServer_Rejects_Continuation0(t *testing.T) {
	synctestTest(t, testServer_Rejects_Continuation0)
}
func testServer_Rejects_Continuation0(t testing.TB) {
	st := newServerTesterForError(t)
	st.fr.AllowIllegalWrites = true
	if err := st.fr.WriteContinuation(0, true, st.encodeHeader()); err != nil {
		t.Fatal(err)
	}
	st.wantGoAway(0, ErrCodeProtocol)
}

// No PRIORITY on stream 0.
func TestServer_Rejects_Priority0(t *testing.T) { synctestTest(t, testServer_Rejects_Priority0) }
func testServer_Rejects_Priority0(t testing.TB) {
	st := newServerTesterForError(t)
	st.fr.AllowIllegalWrites = true
	st.writePriority(0, PriorityParam{StreamDep: 1})
	st.wantGoAway(0, ErrCodeProtocol)
}

// PRIORITY_UPDATE only accepts non-zero ID for the prioritized stream ID in
// its payload.
func TestServer_Rejects_PriorityUpdate0(t *testing.T) {
	synctestTest(t, testServer_Rejects_PriorityUpdate0)
}
func testServer_Rejects_PriorityUpdate0(t testing.TB) {
	st := newServerTesterForError(t)
	st.fr.AllowIllegalWrites = true
	st.writePriorityUpdate(0, "")
	st.wantGoAway(0, ErrCodeProtocol)
}

// PRIORITY_UPDATE with unparsable priority parameters may be rejected.
func TestServer_Rejects_PriorityUpdateUnparsable(t *testing.T) {
	synctestTest(t, testServer_Rejects_PriorityUnparsable)
}
func testServer_Rejects_PriorityUnparsable(t testing.TB) {
	st := newServerTester(t, nil, func(s *Server) {
		s.NewWriteScheduler = NewPriorityWriteSchedulerRFC9218
	})
	defer st.Close()
	st.greet()
	st.writePriorityUpdate(1, "Invalid dictionary: ((((")
	st.wantRSTStream(1, ErrCodeProtocol)
}

// No HEADERS frame with a self-dependence.
func TestServer_Rejects_HeadersSelfDependence(t *testing.T) {
	synctestTest(t, testServer_Rejects_HeadersSelfDependence)
}
func testServer_Rejects_HeadersSelfDependence(t testing.TB) {
	testServerRejectsStream(t, ErrCodeProtocol, func(st *serverTester) {
		st.fr.AllowIllegalWrites = true
		st.writeHeaders(HeadersFrameParam{
			StreamID:      1,
			BlockFragment: st.encodeHeader(),
			EndStream:     true,
			EndHeaders:    true,
			Priority:      PriorityParam{StreamDep: 1},
		})
	})
}

// No PRIORITY frame with a self-dependence.
func TestServer_Rejects_PrioritySelfDependence(t *testing.T) {
	synctestTest(t, testServer_Rejects_PrioritySelfDependence)
}
func testServer_Rejects_PrioritySelfDependence(t testing.TB) {
	testServerRejectsStream(t, ErrCodeProtocol, func(st *serverTester) {
		st.fr.AllowIllegalWrites = true
		st.writePriority(1, PriorityParam{StreamDep: 1})
	})
}

func TestServer_Rejects_PushPromise(t *testing.T) { synctestTest(t, testServer_Rejects_PushPromise) }
func testServer_Rejects_PushPromise(t testing.TB) {
	st := newServerTesterForError(t)
	pp := PushPromiseParam{
		StreamID:  1,
		PromiseID: 3,
	}
	if err := st.fr.WritePushPromise(pp); err != nil {
		t.Fatal(err)
	}
	st.wantGoAway(1, ErrCodeProtocol)
}

// testServerRejectsStream tests that the server sends a RST_STREAM with the provided
// error code after a client sends a bogus request.
func testServerRejectsStream(t testing.TB, code ErrCode, writeReq func(*serverTester)) {
	st := newServerTester(t, func(w http.ResponseWriter, r *http.Request) {})
	defer st.Close()
	st.greet()
	writeReq(st)
	st.wantRSTStream(1, code)
}

// testServerRequest sets up an idle HTTP/2 connection and lets you
// write a single request with writeReq, and then verify that the
// *http.Request is built correctly in checkReq.
func testServerRequest(t testing.TB, writeReq func(*serverTester), checkReq func(*http.Request)) {
	gotReq := make(chan bool, 1)
	st := newServerTester(t, func(w http.ResponseWriter, r *http.Request) {
		if r.Body == nil {
			t.Fatal("nil Body")
		}
		checkReq(r)
		gotReq <- true
	})
	defer st.Close()

	st.greet()
	writeReq(st)
	<-gotReq
}

func getSlash(st *serverTester) { st.bodylessReq1() }

func TestServer_Response_NoData(t *testing.T) { synctestTest(t, testServer_Response_NoData) }
func testServer_Response_NoData(t testing.TB) {
	testServerResponse(t, func(w http.ResponseWriter, r *http.Request) error {
		// Nothing.
		return nil
	}, func(st *serverTester) {
		getSlash(st)
		st.wantHeaders(wantHeader{
			streamID:  1,
			endStream: true,
		})
	})
}

func TestServer_Response_NoData_Header_FooBar(t *testing.T) {
	synctestTest(t, testServer_Response_NoData_Header_FooBar)
}
func testServer_Response_NoData_Header_FooBar(t testing.TB) {
	testServerResponse(t, func(w http.ResponseWriter, r *http.Request) error {
		w.Header().Set("Foo-Bar", "some-value")
		return nil
	}, func(st *serverTester) {
		getSlash(st)
		st.wantHeaders(wantHeader{
			streamID:  1,
			endStream: true,
			header: http.Header{
				":status":        []string{"200"},
				"foo-bar":        []string{"some-value"},
				"content-length": []string{"0"},
			},
		})
	})
}

// Reject content-length headers containing a sign.
// See https://golang.org/issue/39017
func TestServerIgnoresContentLengthSignWhenWritingChunks(t *testing.T) {
	synctestTest(t, testServerIgnoresContentLengthSignWhenWritingChunks)
}
func testServerIgnoresContentLengthSignWhenWritingChunks(t testing.TB) {
	tests := []struct {
		name   string
		cl     string
		wantCL string
	}{
		{
			name:   "proper content-length",
			cl:     "3",
			wantCL: "3",
		},
		{
			name:   "ignore cl with plus sign",
			cl:     "+3",
			wantCL: "0",
		},
		{
			name:   "ignore cl with minus sign",
			cl:     "-3",
			wantCL: "0",
		},
		{
			name:   "max int64, for safe uint64->int64 conversion",
			cl:     "9223372036854775807",
			wantCL: "9223372036854775807",
		},
		{
			name:   "overflows int64, so ignored",
			cl:     "9223372036854775808",
			wantCL: "0",
		},
	}

	for _, tt := range tests {
		testServerResponse(t, func(w http.ResponseWriter, r *http.Request) error {
			w.Header().Set("content-length", tt.cl)
			return nil
		}, func(st *serverTester) {
			getSlash(st)
			st.wantHeaders(wantHeader{
				streamID:  1,
				endStream: true,
				header: http.Header{
					":status":        []string{"200"},
					"content-length": []string{tt.wantCL},
				},
			})
		})
	}
}

// Reject content-length headers containing a sign.
// See https://golang.org/issue/39017
func TestServerRejectsContentLengthWithSignNewRequests(t *testing.T) {
	tests := []struct {
		name   string
		cl     string
		wantCL int64
	}{
		{
			name:   "proper content-length",
			cl:     "3",
			wantCL: 3,
		},
		{
			name:   "ignore cl with plus sign",
			cl:     "+3",
			wantCL: 0,
		},
		{
			name:   "ignore cl with minus sign",
			cl:     "-3",
			wantCL: 0,
		},
		{
			name:   "max int64, for safe uint64->int64 conversion",
			cl:     "9223372036854775807",
			wantCL: 9223372036854775807,
		},
		{
			name:   "overflows int64, so ignored",
			cl:     "9223372036854775808",
			wantCL: 0,
		},
	}

	for _, tt := range tests {
		tt := tt
		synctestSubtest(t, tt.name, func(t testing.TB) {
			writeReq := func(st *serverTester) {
				st.writeHeaders(HeadersFrameParam{
					StreamID:      1, // clients send odd numbers
					BlockFragment: st.encodeHeader("content-length", tt.cl),
					EndStream:     false,
					EndHeaders:    true,
				})
				st.writeData(1, false, []byte(""))
			}
			checkReq := func(r *http.Request) {
				if r.ContentLength != tt.wantCL {
					t.Fatalf("Got: %d\nWant: %d", r.ContentLength, tt.wantCL)
				}
			}
			testServerRequest(t, writeReq, checkReq)
		})
	}
}

func TestServer_Response_Data_Sniff_DoesntOverride(t *testing.T) {
	synctestTest(t, testServer_Response_Data_Sniff_DoesntOverride)
}
func testServer_Response_Data_Sniff_DoesntOverride(t testing.TB) {
	const msg = "<html>this is HTML."
	testServerResponse(t, func(w http.ResponseWriter, r *http.Request) error {
		w.Header().Set("Content-Type", "foo/bar")
		io.WriteString(w, msg)
		return nil
	}, func(st *serverTester) {
		getSlash(st)
		st.wantHeaders(wantHeader{
			streamID:  1,
			endStream: false,
			header: http.Header{
				":status":        []string{"200"},
				"content-type":   []string{"foo/bar"},
				"content-length": []string{strconv.Itoa(len(msg))},
			},
		})
		st.wantData(wantData{
			streamID:  1,
			endStream: true,
			data:      []byte(msg),
		})
	})
}

func TestServer_Response_TransferEncoding_chunked(t *testing.T) {
	synctestTest(t, testServer_Response_TransferEncoding_chunked)
}
func testServer_Response_TransferEncoding_chunked(t testing.TB) {
	const msg = "hi"
	testServerResponse(t, func(w http.ResponseWriter, r *http.Request) error {
		w.Header().Set("Transfer-Encoding", "chunked") // should be stripped
		io.WriteString(w, msg)
		return nil
	}, func(st *serverTester) {
		getSlash(st)
		st.wantHeaders(wantHeader{
			streamID:  1,
			endStream: false,
			header: http.Header{
				":status":        []string{"200"},
				"content-type":   []string{"text/plain; charset=utf-8"},
				"content-length": []string{strconv.Itoa(len(msg))},
			},
		})
	})
}

// Header accessed only after the initial write.
func TestServer_Response_Data_IgnoreHeaderAfterWrite_After(t *testing.T) {
	synctestTest(t, testServer_Response_Data_IgnoreHeaderAfterWrite_After)
}
func testServer_Response_Data_IgnoreHeaderAfterWrite_After(t testing.TB) {
	const msg = "<html>this is HTML."
	testServerResponse(t, func(w http.ResponseWriter, r *http.Request) error {
		io.WriteString(w, msg)
		w.Header().Set("foo", "should be ignored")
		return nil
	}, func(st *serverTester) {
		getSlash(st)
		st.wantHeaders(wantHeader{
			streamID:  1,
			endStream: false,
			header: http.Header{
				":status":        []string{"200"},
				"content-type":   []string{"text/html; charset=utf-8"},
				"content-length": []string{strconv.Itoa(len(msg))},
			},
		})
	})
}

// Header accessed before the initial write and later mutated.
func TestServer_Response_Data_IgnoreHeaderAfterWrite_Overwrite(t *testing.T) {
	synctestTest(t, testServer_Response_Data_IgnoreHeaderAfterWrite_Overwrite)
}
func testServer_Response_Data_IgnoreHeaderAfterWrite_Overwrite(t testing.TB) {
	const msg = "<html>this is HTML."
	testServerResponse(t, func(w http.ResponseWriter, r *http.Request) error {
		w.Header().Set("foo", "proper value")
		io.WriteString(w, msg)
		w.Header().Set("foo", "should be ignored")
		return nil
	}, func(st *serverTester) {
		getSlash(st)
		st.wantHeaders(wantHeader{
			streamID:  1,
			endStream: false,
			header: http.Header{
				":status":        []string{"200"},
				"foo":            []string{"proper value"},
				"content-type":   []string{"text/html; charset=utf-8"},
				"content-length": []string{strconv.Itoa(len(msg))},
			},
		})
	})
}

func TestServer_Response_Data_SniffLenType(t *testing.T) {
	synctestTest(t, testServer_Response_Data_SniffLenType)
}
func testServer_Response_Data_SniffLenType(t testing.TB) {
	const msg = "<html>this is HTML."
	testServerResponse(t, func(w http.ResponseWriter, r *http.Request) error {
		io.WriteString(w, msg)
		return nil
	}, func(st *serverTester) {
		getSlash(st)
		st.wantHeaders(wantHeader{
			streamID:  1,
			endStream: false,
			header: http.Header{
				":status":        []string{"200"},
				"content-type":   []string{"text/html; charset=utf-8"},
				"content-length": []string{strconv.Itoa(len(msg))},
			},
		})
		st.wantData(wantData{
			streamID:  1,
			endStream: true,
			data:      []byte(msg),
		})
	})
}

func TestServer_Response_Header_Flush_MidWrite(t *testing.T) {
	synctestTest(t, testServer_Response_Header_Flush_MidWrite)
}
func testServer_Response_Header_Flush_MidWrite(t testing.TB) {
	const msg = "<html>this is HTML"
	const msg2 = ", and this is the next chunk"
	testServerResponse(t, func(w http.ResponseWriter, r *http.Request) error {
		io.WriteString(w, msg)
		w.(http.Flusher).Flush()
		io.WriteString(w, msg2)
		return nil
	}, func(st *serverTester) {
		getSlash(st)
		st.wantHeaders(wantHeader{
			streamID:  1,
			endStream: false,
			header: http.Header{
				":status":      []string{"200"},
				"content-type": []string{"text/html; charset=utf-8"}, // sniffed
				// and no content-length
			},
		})
		st.wantData(wantData{
			streamID:  1,
			endStream: false,
			data:      []byte(msg),
		})
		st.wantData(wantData{
			streamID:  1,
			endStream: true,
			data:      []byte(msg2),
		})
	})
}

func TestServer_Response_LargeWrite(t *testing.T) { synctestTest(t, testServer_Response_LargeWrite) }
func testServer_Response_LargeWrite(t testing.TB) {
	const size = 1 << 20
	const maxFrameSize = 16 << 10
	testServerResponse(t, func(w http.ResponseWriter, r *http.Request) error {
		n, err := w.Write(bytes.Repeat([]byte("a"), size))
		if err != nil {
			return fmt.Errorf("Write error: %v", err)
		}
		if n != size {
			return fmt.Errorf("wrong size %d from Write", n)
		}
		return nil
	}, func(st *serverTester) {
		if err := st.fr.WriteSettings(
			Setting{SettingInitialWindowSize, 0},
			Setting{SettingMaxFrameSize, maxFrameSize},
		); err != nil {
			t.Fatal(err)
		}
		st.wantSettingsAck()

		getSlash(st) // make the single request

		// Give the handler quota to write:
		if err := st.fr.WriteWindowUpdate(1, size); err != nil {
			t.Fatal(err)
		}
		// Give the handler quota to write to connection-level
		// window as well
		if err := st.fr.WriteWindowUpdate(0, size); err != nil {
			t.Fatal(err)
		}
		st.wantHeaders(wantHeader{
			streamID:  1,
			endStream: false,
			header: http.Header{
				":status":      []string{"200"},
				"content-type": []string{"text/plain; charset=utf-8"}, // sniffed
				// and no content-length
			},
		})
		var bytes, frames int
		for {
			df := readFrame[*DataFrame](t, st)
			bytes += len(df.Data())
			frames++
			for _, b := range df.Data() {
				if b != 'a' {
					t.Fatal("non-'a' byte seen in DATA")
				}
			}
			if df.StreamEnded() {
				break
			}
		}
		if bytes != size {
			t.Errorf("Got %d bytes; want %d", bytes, size)
		}
		if want := int(size / maxFrameSize); frames < want || frames > want*2 {
			t.Errorf("Got %d frames; want %d", frames, size)
		}
	})
}

// Test that the handler can't write more than the client allows
func TestServer_Response_LargeWrite_FlowControlled(t *testing.T) {
	synctestTest(t, testServer_Response_LargeWrite_FlowControlled)
}
func testServer_Response_LargeWrite_FlowControlled(t testing.TB) {
	// Make these reads. Before each read, the client adds exactly enough
	// flow-control to satisfy the read. Numbers chosen arbitrarily.
	reads := []int{123, 1, 13, 127}
	size := 0
	for _, n := range reads {
		size += n
	}

	testServerResponse(t, func(w http.ResponseWriter, r *http.Request) error {
		w.(http.Flusher).Flush()
		n, err := w.Write(bytes.Repeat([]byte("a"), size))
		if err != nil {
			return fmt.Errorf("Write error: %v", err)
		}
		if n != size {
			return fmt.Errorf("wrong size %d from Write", n)
		}
		return nil
	}, func(st *serverTester) {
		// Set the window size to something explicit for this test.
		// It's also how much initial data we expect.
		if err := st.fr.WriteSettings(Setting{SettingInitialWindowSize, uint32(reads[0])}); err != nil {
			t.Fatal(err)
		}
		st.wantSettingsAck()

		getSlash(st) // make the single request

		st.wantHeaders(wantHeader{
			streamID:  1,
			endStream: false,
		})

		st.wantData(wantData{
			streamID:  1,
			endStream: false,
			size:      reads[0],
		})

		for i, quota := range reads[1:] {
			if err := st.fr.WriteWindowUpdate(1, uint32(quota)); err != nil {
				t.Fatal(err)
			}
			st.wantData(wantData{
				streamID:  1,
				endStream: i == len(reads[1:])-1,
				size:      quota,
			})
		}
	})
}

// Test that the handler blocked in a Write is unblocked if the server sends a RST_STREAM.
func TestServer_Response_RST_Unblocks_LargeWrite(t *testing.T) {
	synctestTest(t, testServer_Response_RST_Unblocks_LargeWrite)
}
func testServer_Response_RST_Unblocks_LargeWrite(t testing.TB) {
	const size = 1 << 20
	const maxFrameSize = 16 << 10
	testServerResponse(t, func(w http.ResponseWriter, r *http.Request) error {
		w.(http.Flusher).Flush()
		_, err := w.Write(bytes.Repeat([]byte("a"), size))
		if err == nil {
			return errors.New("unexpected nil error from Write in handler")
		}
		return nil
	}, func(st *serverTester) {
		if err := st.fr.WriteSettings(
			Setting{SettingInitialWindowSize, 0},
			Setting{SettingMaxFrameSize, maxFrameSize},
		); err != nil {
			t.Fatal(err)
		}
		st.wantSettingsAck()

		getSlash(st) // make the single request

		st.wantHeaders(wantHeader{
			streamID:  1,
			endStream: false,
		})

		if err := st.fr.WriteRSTStream(1, ErrCodeCancel); err != nil {
			t.Fatal(err)
		}
	})
}

func TestServer_Response_Empty_Data_Not_FlowControlled(t *testing.T) {
	synctestTest(t, testServer_Response_Empty_Data_Not_FlowControlled)
}
func testServer_Response_Empty_Data_Not_FlowControlled(t testing.TB) {
	testServerResponse(t, func(w http.ResponseWriter, r *http.Request) error {
		w.(http.Flusher).Flush()
		// Nothing; send empty DATA
		return nil
	}, func(st *serverTester) {
		// Handler gets no data quota:
		if err := st.fr.WriteSettings(Setting{SettingInitialWindowSize, 0}); err != nil {
			t.Fatal(err)
		}
		st.wantSettingsAck()

		getSlash(st) // make the single request

		st.wantHeaders(wantHeader{
			streamID:  1,
			endStream: false,
		})

		st.wantData(wantData{
			streamID:  1,
			endStream: true,
			size:      0,
		})
	})
}

func TestServer_Response_Automatic100Continue(t *testing.T) {
	synctestTest(t, testServer_Response_Automatic100Continue)
}
func testServer_Response_Automatic100Continue(t testing.TB) {
	const msg = "foo"
	const reply = "bar"
	testServerResponse(t, func(w http.ResponseWriter, r *http.Request) error {
		if v := r.Header.Get("Expect"); v != "" {
			t.Errorf("Expect header = %q; want empty", v)
		}
		buf := make([]byte, len(msg))
		// This read should trigger the 100-continue being sent.
		if n, err := io.ReadFull(r.Body, buf); err != nil || n != len(msg) || string(buf) != msg {
			return fmt.Errorf("ReadFull = %q, %v; want %q, nil", buf[:n], err, msg)
		}
		_, err := io.WriteString(w, reply)
		return err
	}, func(st *serverTester) {
		st.writeHeaders(HeadersFrameParam{
			StreamID:      1, // clients send odd numbers
			BlockFragment: st.encodeHeader(":method", "POST", "expect", "100-Continue"),
			EndStream:     false,
			EndHeaders:    true,
		})
		st.wantHeaders(wantHeader{
			streamID:  1,
			endStream: false,
			header: http.Header{
				":status": []string{"100"},
			},
		})

		// Okay, they sent status 100, so we can send our
		// gigantic and/or sensitive "foo" payload now.
		st.writeData(1, true, []byte(msg))

		st.wantHeaders(wantHeader{
			streamID:  1,
			endStream: false,
			header: http.Header{
				":status":        []string{"200"},
				"content-type":   []string{"text/plain; charset=utf-8"},
				"content-length": []string{strconv.Itoa(len(reply))},
			},
		})

		st.wantData(wantData{
			streamID:  1,
			endStream: true,
			data:      []byte(reply),
		})
	})
}

func TestServer_HandlerWriteErrorOnDisconnect(t *testing.T) {
	synctestTest(t, testServer_HandlerWriteErrorOnDisconnect)
}
func testServer_HandlerWriteErrorOnDisconnect(t testing.TB) {
	errc := make(chan error, 1)
	testServerResponse(t, func(w http.ResponseWriter, r *http.Request) error {
		p := []byte("some data.\n")
		for {
			_, err := w.Write(p)
			if err != nil {
				errc <- err
				return nil
			}
		}
	}, func(st *serverTester) {
		st.writeHeaders(HeadersFrameParam{
			StreamID:      1,
			BlockFragment: st.encodeHeader(),
			EndStream:     false,
			EndHeaders:    true,
		})
		st.wantHeaders(wantHeader{
			streamID:  1,
			endStream: false,
		})
		// Close the connection and wait for the handler to (hopefully) notice.
		st.cc.Close()
		_ = <-errc
	})
}

func TestServer_Rejects_Too_Many_Streams(t *testing.T) {
	synctestTest(t, testServer_Rejects_Too_Many_Streams)
}
func testServer_Rejects_Too_Many_Streams(t testing.TB) {
	st := newServerTester(t, nil)
	st.greet()
	nextStreamID := uint32(1)
	streamID := func() uint32 {
		defer func() { nextStreamID += 2 }()
		return nextStreamID
	}
	sendReq := func(id uint32) {
		st.writeHeaders(HeadersFrameParam{
			StreamID: id,
			BlockFragment: st.encodeHeader(
				":path", fmt.Sprintf("/%v", id),
			),
			EndStream:  true,
			EndHeaders: true,
		})
	}
	var calls []*serverHandlerCall
	for i := 0; i < DefaultMaxStreams; i++ {
		sendReq(streamID())
		calls = append(calls, st.nextHandlerCall())
	}

	// And this one should cross the limit:
	// (It's also sent as a CONTINUATION, to verify we still track the decoder context,
	// even if we're rejecting it)
	rejectID := streamID()
	headerBlock := st.encodeHeader(":path", fmt.Sprintf("/%v", rejectID))
	frag1, frag2 := headerBlock[:3], headerBlock[3:]
	st.writeHeaders(HeadersFrameParam{
		StreamID:      rejectID,
		BlockFragment: frag1,
		EndStream:     true,
		EndHeaders:    false, // CONTINUATION coming
	})
	if err := st.fr.WriteContinuation(rejectID, true, frag2); err != nil {
		t.Fatal(err)
	}
	st.sync()
	st.wantRSTStream(rejectID, ErrCodeProtocol)

	// But let a handler finish:
	calls[0].exit()
	st.sync()
	st.wantHeaders(wantHeader{
		streamID:  1,
		endStream: true,
	})

	// And now another stream should be able to start:
	goodID := streamID()
	sendReq(goodID)
	call := st.nextHandlerCall()
	if got, want := call.req.URL.Path, fmt.Sprintf("/%d", goodID); got != want {
		t.Errorf("Got request for %q, want %q", got, want)
	}
}

// So many response headers that the server needs to use CONTINUATION frames:
func TestServer_Response_ManyHeaders_With_Continuation(t *testing.T) {
	synctestTest(t, testServer_Response_ManyHeaders_With_Continuation)
}
func testServer_Response_ManyHeaders_With_Continuation(t testing.TB) {
	testServerResponse(t, func(w http.ResponseWriter, r *http.Request) error {
		h := w.Header()
		for i := 0; i < 5000; i++ {
			h.Set(fmt.Sprintf("x-header-%d", i), fmt.Sprintf("x-value-%d", i))
		}
		return nil
	}, func(st *serverTester) {
		getSlash(st)
		hf := readFrame[*HeadersFrame](t, st)
		if hf.HeadersEnded() {
			t.Fatal("got unwanted END_HEADERS flag")
		}
		n := 0
		for {
			n++
			cf := readFrame[*ContinuationFrame](t, st)
			if cf.HeadersEnded() {
				break
			}
		}
		if n < 5 {
			t.Errorf("Only got %d CONTINUATION frames; expected 5+ (currently 6)", n)
		}
	})
}

// This previously crashed (reported by Mathieu Lonjaret as observed
// while using Camlistore) because we got a DATA frame from the client
// after the handler exited and our logic at the time was wrong,
// keeping a stream in the map in stateClosed, which tickled an
// invariant check later when we tried to remove that stream (via
// defer sc.closeAllStreamsOnConnClose) when the serverConn serve loop
// ended.
func TestServer_NoCrash_HandlerClose_Then_ClientClose(t *testing.T) {
	synctestTest(t, testServer_NoCrash_HandlerClose_Then_ClientClose)
}
func testServer_NoCrash_HandlerClose_Then_ClientClose(t testing.TB) {
	testServerResponse(t, func(w http.ResponseWriter, r *http.Request) error {
		// nothing
		return nil
	}, func(st *serverTester) {
		st.writeHeaders(HeadersFrameParam{
			StreamID:      1,
			BlockFragment: st.encodeHeader(),
			EndStream:     false, // DATA is coming
			EndHeaders:    true,
		})
		st.wantHeaders(wantHeader{
			streamID:  1,
			endStream: true,
		})

		// Sent when the a Handler closes while a client has
		// indicated it's still sending DATA:
		st.wantRSTStream(1, ErrCodeNo)

		// Now the handler has ended, so it's ended its
		// stream, but the client hasn't closed its side
		// (stateClosedLocal).  So send more data and verify
		// it doesn't crash with an internal invariant panic, like
		// it did before.
		st.writeData(1, true, []byte("foo"))

		// Sent after a peer sends data anyway (admittedly the
		// previous RST_STREAM might've still been in-flight),
		// but they'll get the more friendly 'cancel' code
		// first.
		st.wantRSTStream(1, ErrCodeStreamClosed)

		// We should have our flow control bytes back,
		// since the handler didn't get them.
		st.wantConnFlowControlConsumed(0)

		// Set up a bunch of machinery to record the panic we saw
		// previously.
		var (
			panMu    sync.Mutex
			panicVal interface{}
		)

		SetTestHookOnPanic(t, func(sc *ServerConn, pv interface{}) bool {
			panMu.Lock()
			panicVal = pv
			panMu.Unlock()
			return true
		})

		// Now force the serve loop to end, via closing the connection.
		st.cc.Close()
		synctest.Wait()

		panMu.Lock()
		got := panicVal
		panMu.Unlock()
		if got != nil {
			t.Errorf("Got panic: %v", got)
		}
	})
}

func TestServer_Rejects_TLS10(t *testing.T) { testRejectTLS(t, tls.VersionTLS10) }
func TestServer_Rejects_TLS11(t *testing.T) { testRejectTLS(t, tls.VersionTLS11) }

func testRejectTLS(t *testing.T, version uint16) {
	synctestTest(t, func(t testing.TB) {
		st := newServerTester(t, nil, func(state *tls.ConnectionState) {
			// As of 1.18 the default minimum Go TLS version is
			// 1.2. In order to test rejection of lower versions,
			// manually set the version to 1.0
			state.Version = version
		})
		defer st.Close()
		st.wantGoAway(0, ErrCodeInadequateSecurity)
	})
}

func TestServer_Rejects_TLSBadCipher(t *testing.T) { synctestTest(t, testServer_Rejects_TLSBadCipher) }
func testServer_Rejects_TLSBadCipher(t testing.TB) {
	st := newServerTester(t, nil, func(state *tls.ConnectionState) {
		state.Version = tls.VersionTLS12
		state.CipherSuite = tls.TLS_RSA_WITH_RC4_128_SHA
	})
	defer st.Close()
	st.wantGoAway(0, ErrCodeInadequateSecurity)
}

func TestServer_Advertises_Common_Cipher(t *testing.T) {
	synctestTest(t, testServer_Advertises_Common_Cipher)
}
func testServer_Advertises_Common_Cipher(t testing.TB) {
	ts := newTestServer(t, func(w http.ResponseWriter, r *http.Request) {
	}, func(srv *http.Server) {
		// Have the server configured with no specific cipher suites.
		// This tests that Go's defaults include the required one.
		srv.TLSConfig = nil
	})

	// Have the client only support the one required by the spec.
	const requiredSuite = tls.TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256
	tlsConfig := tlsConfigInsecure.Clone()
	tlsConfig.MaxVersion = tls.VersionTLS12
	tlsConfig.CipherSuites = []uint16{requiredSuite}
	tr := &Transport{TLSClientConfig: tlsConfig}
	defer tr.CloseIdleConnections()

	req, err := http.NewRequest("GET", ts.URL, nil)
	if err != nil {
		t.Fatal(err)
	}
	res, err := tr.RoundTrip(req)
	if err != nil {
		t.Fatal(err)
	}
	res.Body.Close()
}

// testServerResponse sets up an idle HTTP/2 connection. The client function should
// write a single request that must be handled by the handler.
func testServerResponse(t testing.TB,
	handler func(http.ResponseWriter, *http.Request) error,
	client func(*serverTester),
) {
	errc := make(chan error, 1)
	st := newServerTester(t, func(w http.ResponseWriter, r *http.Request) {
		if r.Body == nil {
			t.Fatal("nil Body")
		}
		err := handler(w, r)
		select {
		case errc <- err:
		default:
			t.Errorf("unexpected duplicate request")
		}
	})
	defer st.Close()

	st.greet()
	client(st)

	if err := <-errc; err != nil {
		t.Fatalf("Error in handler: %v", err)
	}
}

// readBodyHandler returns an http Handler func that reads len(want)
// bytes from r.Body and fails t if the contents read were not
// the value of want.
func readBodyHandler(t testing.TB, want string) func(w http.ResponseWriter, r *http.Request) {
	return func(w http.ResponseWriter, r *http.Request) {
		buf := make([]byte, len(want))
		_, err := io.ReadFull(r.Body, buf)
		if err != nil {
			t.Error(err)
			return
		}
		if string(buf) != want {
			t.Errorf("read %q; want %q", buf, want)
		}
	}
}

func TestServer_MaxDecoderHeaderTableSize(t *testing.T) {
	synctestTest(t, testServer_MaxDecoderHeaderTableSize)
}
func testServer_MaxDecoderHeaderTableSize(t testing.TB) {
	wantHeaderTableSize := uint32(InitialHeaderTableSize * 2)
	st := newServerTester(t, func(w http.ResponseWriter, r *http.Request) {}, func(s *Server) {
		s.MaxDecoderHeaderTableSize = wantHeaderTableSize
	})
	defer st.Close()

	var advHeaderTableSize *uint32
	st.greetAndCheckSettings(func(s Setting) error {
		switch s.ID {
		case SettingHeaderTableSize:
			advHeaderTableSize = &s.Val
		}
		return nil
	})

	if advHeaderTableSize == nil {
		t.Errorf("server didn't advertise a header table size")
	} else if got, want := *advHeaderTableSize, wantHeaderTableSize; got != want {
		t.Errorf("server advertised a header table size of %d, want %d", got, want)
	}
}

func TestServer_MaxEncoderHeaderTableSize(t *testing.T) {
	synctestTest(t, testServer_MaxEncoderHeaderTableSize)
}
func testServer_MaxEncoderHeaderTableSize(t testing.TB) {
	wantHeaderTableSize := uint32(InitialHeaderTableSize / 2)
	st := newServerTester(t, func(w http.ResponseWriter, r *http.Request) {}, func(s *Server) {
		s.MaxEncoderHeaderTableSize = wantHeaderTableSize
	})
	defer st.Close()

	st.greet()

	if got, want := st.sc.TestHPACKEncoder().MaxDynamicTableSize(), wantHeaderTableSize; got != want {
		t.Errorf("server encoder is using a header table size of %d, want %d", got, want)
	}
}

// Issue 12843
func TestServerDoS_MaxHeaderListSize(t *testing.T) { synctestTest(t, testServerDoS_MaxHeaderListSize) }
func testServerDoS_MaxHeaderListSize(t testing.TB) {
	st := newServerTester(t, func(w http.ResponseWriter, r *http.Request) {})
	defer st.Close()

	// shake hands
	frameSize := DefaultMaxReadFrameSize
	var advHeaderListSize *uint32
	st.greetAndCheckSettings(func(s Setting) error {
		switch s.ID {
		case SettingMaxFrameSize:
			if s.Val < MinMaxFrameSize {
				frameSize = MinMaxFrameSize
			} else if s.Val > MaxFrameSize {
				frameSize = MaxFrameSize
			} else {
				frameSize = int(s.Val)
			}
		case SettingMaxHeaderListSize:
			advHeaderListSize = &s.Val
		}
		return nil
	})

	if advHeaderListSize == nil {
		t.Errorf("server didn't advertise a max header list size")
	} else if *advHeaderListSize == 0 {
		t.Errorf("server advertised a max header list size of 0")
	}

	st.encodeHeaderField(":method", "GET")
	st.encodeHeaderField(":path", "/")
	st.encodeHeaderField(":scheme", "https")
	cookie := strings.Repeat("*", 4058)
	st.encodeHeaderField("cookie", cookie)
	st.writeHeaders(HeadersFrameParam{
		StreamID:      1,
		BlockFragment: st.headerBuf.Bytes(),
		EndStream:     true,
		EndHeaders:    false,
	})

	// Capture the short encoding of a duplicate ~4K cookie, now
	// that we've already sent it once.
	st.headerBuf.Reset()
	st.encodeHeaderField("cookie", cookie)

	// Now send 1MB of it.
	const size = 1 << 20
	b := bytes.Repeat(st.headerBuf.Bytes(), size/st.headerBuf.Len())
	for len(b) > 0 {
		chunk := b
		if len(chunk) > frameSize {
			chunk = chunk[:frameSize]
		}
		b = b[len(chunk):]
		st.fr.WriteContinuation(1, len(b) == 0, chunk)
	}

	st.wantHeaders(wantHeader{
		streamID:  1,
		endStream: false,
		header: http.Header{
			":status":        []string{"431"},
			"content-type":   []string{"text/html; charset=utf-8"},
			"content-length": []string{"63"},
		},
	})
}

func TestServer_Response_Stream_With_Missing_Trailer(t *testing.T) {
	synctestTest(t, testServer_Response_Stream_With_Missing_Trailer)
}
func testServer_Response_Stream_With_Missing_Trailer(t testing.TB) {
	testServerResponse(t, func(w http.ResponseWriter, r *http.Request) error {
		w.Header().Set("Trailer", "test-trailer")
		return nil
	}, func(st *serverTester) {
		getSlash(st)
		st.wantHeaders(wantHeader{
			streamID:  1,
			endStream: false,
		})
		st.wantData(wantData{
			streamID:  1,
			endStream: true,
			size:      0,
		})
	})
}

func TestCompressionErrorOnWrite(t *testing.T) { synctestTest(t, testCompressionErrorOnWrite) }
func testCompressionErrorOnWrite(t testing.TB) {
	const maxStrLen = 8 << 10
	var serverConfig *http.Server
	st := newServerTester(t, func(w http.ResponseWriter, r *http.Request) {
		// No response body.
	}, func(s *http.Server) {
		serverConfig = s
		serverConfig.MaxHeaderBytes = maxStrLen
	})
	st.addLogFilter("connection error: COMPRESSION_ERROR")
	defer st.Close()
	st.greet()

	maxAllowed := st.sc.TestFramerMaxHeaderStringLen()

	// Crank this up, now that we have a conn connected with the
	// hpack.Decoder's max string length set has been initialized
	// from the earlier low ~8K value. We want this higher so don't
	// hit the max header list size. We only want to test hitting
	// the max string size.
	serverConfig.MaxHeaderBytes = 1 << 20

	// First a request with a header that's exactly the max allowed size
	// for the hpack compression. It's still too long for the header list
	// size, so we'll get the 431 error, but that keeps the compression
	// context still valid.
	hbf := st.encodeHeader("foo", strings.Repeat("a", maxAllowed))

	st.writeHeaders(HeadersFrameParam{
		StreamID:      1,
		BlockFragment: hbf,
		EndStream:     true,
		EndHeaders:    true,
	})
	st.wantHeaders(wantHeader{
		streamID:  1,
		endStream: false,
		header: http.Header{
			":status":        []string{"431"},
			"content-type":   []string{"text/html; charset=utf-8"},
			"content-length": []string{"63"},
		},
	})
	df := readFrame[*DataFrame](t, st)
	if !strings.Contains(string(df.Data()), "HTTP Error 431") {
		t.Errorf("Unexpected data body: %q", df.Data())
	}
	if !df.StreamEnded() {
		t.Fatalf("expect data stream end")
	}

	// And now send one that's just one byte too big.
	hbf = st.encodeHeader("bar", strings.Repeat("b", maxAllowed+1))
	st.writeHeaders(HeadersFrameParam{
		StreamID:      3,
		BlockFragment: hbf,
		EndStream:     true,
		EndHeaders:    true,
	})
	st.wantGoAway(3, ErrCodeCompression)
}

func TestCompressionErrorOnClose(t *testing.T) { synctestTest(t, testCompressionErrorOnClose) }
func testCompressionErrorOnClose(t testing.TB) {
	st := newServerTester(t, func(w http.ResponseWriter, r *http.Request) {
		// No response body.
	})
	st.addLogFilter("connection error: COMPRESSION_ERROR")
	defer st.Close()
	st.greet()

	hbf := st.encodeHeader("foo", "bar")
	hbf = hbf[:len(hbf)-1] // truncate one byte from the end, so hpack.Decoder.Close fails.
	st.writeHeaders(HeadersFrameParam{
		StreamID:      1,
		BlockFragment: hbf,
		EndStream:     true,
		EndHeaders:    true,
	})
	st.wantGoAway(1, ErrCodeCompression)
}

// test that a server handler can read trailers from a client
func TestServerReadsTrailers(t *testing.T) { synctestTest(t, testServerReadsTrailers) }
func testServerReadsTrailers(t testing.TB) {
	const testBody = "some test body"
	writeReq := func(st *serverTester) {
		st.writeHeaders(HeadersFrameParam{
			StreamID:      1, // clients send odd numbers
			BlockFragment: st.encodeHeader("trailer", "Foo, Bar", "trailer", "Baz"),
			EndStream:     false,
			EndHeaders:    true,
		})
		st.writeData(1, false, []byte(testBody))
		st.writeHeaders(HeadersFrameParam{
			StreamID: 1, // clients send odd numbers
			BlockFragment: st.encodeHeaderRaw(
				"foo", "foov",
				"bar", "barv",
				"baz", "bazv",
				"surprise", "wasn't declared; shouldn't show up",
			),
			EndStream:  true,
			EndHeaders: true,
		})
	}
	checkReq := func(r *http.Request) {
		wantTrailer := http.Header{
			"Foo": nil,
			"Bar": nil,
			"Baz": nil,
		}
		if !reflect.DeepEqual(r.Trailer, wantTrailer) {
			t.Errorf("initial Trailer = %v; want %v", r.Trailer, wantTrailer)
		}
		slurp, err := io.ReadAll(r.Body)
		if string(slurp) != testBody {
			t.Errorf("read body %q; want %q", slurp, testBody)
		}
		if err != nil {
			t.Fatalf("Body slurp: %v", err)
		}
		wantTrailerAfter := http.Header{
			"Foo": {"foov"},
			"Bar": {"barv"},
			"Baz": {"bazv"},
		}
		if !reflect.DeepEqual(r.Trailer, wantTrailerAfter) {
			t.Errorf("final Trailer = %v; want %v", r.Trailer, wantTrailerAfter)
		}
	}
	testServerRequest(t, writeReq, checkReq)
}

// test that a server handler can send trailers
func TestServerWritesTrailers_WithFlush(t *testing.T) {
	synctestTest(t, func(t testing.TB) {
		testServerWritesTrailers(t, true)
	})
}
func TestServerWritesTrailers_WithoutFlush(t *testing.T) {
	synctestTest(t, func(t testing.TB) {
		testServerWritesTrailers(t, false)
	})
}

func testServerWritesTrailers(t testing.TB, withFlush bool) {
	// See https://httpwg.github.io/specs/rfc7540.html#rfc.section.8.1.3
	testServerResponse(t, func(w http.ResponseWriter, r *http.Request) error {
		w.Header().Set("Trailer", "Server-Trailer-A, Server-Trailer-B")
		w.Header().Add("Trailer", "Server-Trailer-C")
		w.Header().Add("Trailer", "Transfer-Encoding, Content-Length, Trailer") // filtered

		// Regular headers:
		w.Header().Set("Foo", "Bar")
		w.Header().Set("Content-Length", "5") // len("Hello")

		io.WriteString(w, "Hello")
		if withFlush {
			w.(http.Flusher).Flush()
		}
		w.Header().Set("Server-Trailer-A", "valuea")
		w.Header().Set("Server-Trailer-C", "valuec") // skipping B
		// After a flush, random keys like Server-Surprise shouldn't show up:
		w.Header().Set("Server-Surpise", "surprise! this isn't predeclared!")
		// But we do permit promoting keys to trailers after a
		// flush if they start with the magic
		// otherwise-invalid "Trailer:" prefix:
		w.Header().Set("Trailer:Post-Header-Trailer", "hi1")
		w.Header().Set("Trailer:post-header-trailer2", "hi2")
		w.Header().Set("Trailer:Range", "invalid")
		w.Header().Set("Trailer:Foo\x01Bogus", "invalid")
		w.Header().Set("Transfer-Encoding", "should not be included; Forbidden by RFC 7230 4.1.2")
		w.Header().Set("Content-Length", "should not be included; Forbidden by RFC 7230 4.1.2")
		w.Header().Set("Trailer", "should not be included; Forbidden by RFC 7230 4.1.2")
		return nil
	}, func(st *serverTester) {
		// Ignore errors from writing invalid trailers.
		st.h1server.ErrorLog = log.New(io.Discard, "", 0)
		getSlash(st)
		st.wantHeaders(wantHeader{
			streamID:  1,
			endStream: false,
			header: http.Header{
				":status": []string{"200"},
				"foo":     []string{"Bar"},
				"trailer": []string{
					"Server-Trailer-A, Server-Trailer-B",
					"Server-Trailer-C",
					"Transfer-Encoding, Content-Length, Trailer",
				},
				"content-type":   []string{"text/plain; charset=utf-8"},
				"content-length": []string{"5"},
			},
		})
		st.wantData(wantData{
			streamID:  1,
			endStream: false,
			data:      []byte("Hello"),
		})
		st.wantHeaders(wantHeader{
			streamID:  1,
			endStream: true,
			header: http.Header{
				"post-header-trailer":  []string{"hi1"},
				"post-header-trailer2": []string{"hi2"},
				"server-trailer-a":     []string{"valuea"},
				"server-trailer-c":     []string{"valuec"},
			},
		})
	})
}

func TestServerWritesUndeclaredTrailers(t *testing.T) {
	synctestTest(t, testServerWritesUndeclaredTrailers)
}
func testServerWritesUndeclaredTrailers(t testing.TB) {
	const trailer = "Trailer-Header"
	const value = "hi1"
	ts := newTestServer(t, func(w http.ResponseWriter, r *http.Request) {
		w.Header().Set(http.TrailerPrefix+trailer, value)
	})

	tr := &Transport{TLSClientConfig: tlsConfigInsecure}
	defer tr.CloseIdleConnections()

	cl := &http.Client{Transport: tr}
	resp, err := cl.Get(ts.URL)
	if err != nil {
		t.Fatal(err)
	}
	io.Copy(io.Discard, resp.Body)
	resp.Body.Close()

	if got, want := resp.Trailer.Get(trailer), value; got != want {
		t.Errorf("trailer %v = %q, want %q", trailer, got, want)
	}
}

// validate transmitted header field names & values
// golang.org/issue/14048
func TestServerDoesntWriteInvalidHeaders(t *testing.T) {
	synctestTest(t, testServerDoesntWriteInvalidHeaders)
}
func testServerDoesntWriteInvalidHeaders(t testing.TB) {
	testServerResponse(t, func(w http.ResponseWriter, r *http.Request) error {
		w.Header().Add("OK1", "x")
		w.Header().Add("Bad:Colon", "x") // colon (non-token byte) in key
		w.Header().Add("Bad1\x00", "x")  // null in key
		w.Header().Add("Bad2", "x\x00y") // null in value
		return nil
	}, func(st *serverTester) {
		getSlash(st)
		st.wantHeaders(wantHeader{
			streamID:  1,
			endStream: true,
			header: http.Header{
				":status":        []string{"200"},
				"ok1":            []string{"x"},
				"content-length": []string{"0"},
			},
		})
	})
}

func BenchmarkServerGets(b *testing.B) {
	DisableGoroutineTracking(b)
	b.ReportAllocs()

	const msg = "Hello, world"
	st := newServerTesterWithRealConn(b, func(w http.ResponseWriter, r *http.Request) {
		io.WriteString(w, msg)
	})
	defer st.Close()
	st.greet()

	// Give the server quota to reply. (plus it has the 64KB)
	if err := st.fr.WriteWindowUpdate(0, uint32(b.N*len(msg))); err != nil {
		b.Fatal(err)
	}

	for i := 0; i < b.N; i++ {
		id := 1 + uint32(i)*2
		st.writeHeaders(HeadersFrameParam{
			StreamID:      id,
			BlockFragment: st.encodeHeader(),
			EndStream:     true,
			EndHeaders:    true,
		})
		st.wantFrameType(FrameHeaders)
		if df := readFrame[*DataFrame](b, st); !df.StreamEnded() {
			b.Fatalf("DATA didn't have END_STREAM; got %v", df)
		}
	}
}

func BenchmarkServerPosts(b *testing.B) {
	DisableGoroutineTracking(b)
	b.ReportAllocs()

	const msg = "Hello, world"
	st := newServerTesterWithRealConn(b, func(w http.ResponseWriter, r *http.Request) {
		// Consume the (empty) body from th peer before replying, otherwise
		// the server will sometimes (depending on scheduling) send the peer a
		// a RST_STREAM with the CANCEL error code.
		if n, err := io.Copy(io.Discard, r.Body); n != 0 || err != nil {
			b.Errorf("Copy error; got %v, %v; want 0, nil", n, err)
		}
		io.WriteString(w, msg)
	})
	defer st.Close()
	st.greet()

	// Give the server quota to reply. (plus it has the 64KB)
	if err := st.fr.WriteWindowUpdate(0, uint32(b.N*len(msg))); err != nil {
		b.Fatal(err)
	}

	for i := 0; i < b.N; i++ {
		id := 1 + uint32(i)*2
		st.writeHeaders(HeadersFrameParam{
			StreamID:      id,
			BlockFragment: st.encodeHeader(":method", "POST"),
			EndStream:     false,
			EndHeaders:    true,
		})
		st.writeData(id, true, nil)
		st.wantFrameType(FrameHeaders)
		if df := readFrame[*DataFrame](b, st); !df.StreamEnded() {
			b.Fatalf("DATA didn't have END_STREAM; got %v", df)
		}
	}
}

// Send a stream of messages from server to client in separate data frames.
// Brings up performance issues seen in long streams.
// Created to show problem in go issue #18502
func BenchmarkServerToClientStreamDefaultOptions(b *testing.B) {
	benchmarkServerToClientStream(b)
}

// Justification for Change-Id: Iad93420ef6c3918f54249d867098f1dadfa324d8
// Expect to see memory/alloc reduction by opting in to Frame reuse with the Framer.
func BenchmarkServerToClientStreamReuseFrames(b *testing.B) {
	benchmarkServerToClientStream(b, optFramerReuseFrames)
}

func benchmarkServerToClientStream(b *testing.B, newServerOpts ...interface{}) {
	DisableGoroutineTracking(b)
	b.ReportAllocs()
	const msgLen = 1
	// default window size
	const windowSize = 1<<16 - 1

	// next message to send from the server and for the client to expect
	nextMsg := func(i int) []byte {
		msg := make([]byte, msgLen)
		msg[0] = byte(i)
		if len(msg) != msgLen {
			panic("invalid test setup msg length")
		}
		return msg
	}

	st := newServerTesterWithRealConn(b, func(w http.ResponseWriter, r *http.Request) {
		// Consume the (empty) body from th peer before replying, otherwise
		// the server will sometimes (depending on scheduling) send the peer a
		// a RST_STREAM with the CANCEL error code.
		if n, err := io.Copy(io.Discard, r.Body); n != 0 || err != nil {
			b.Errorf("Copy error; got %v, %v; want 0, nil", n, err)
		}
		for i := 0; i < b.N; i += 1 {
			w.Write(nextMsg(i))
			w.(http.Flusher).Flush()
		}
	}, newServerOpts...)
	defer st.Close()
	st.greet()

	const id = uint32(1)

	st.writeHeaders(HeadersFrameParam{
		StreamID:      id,
		BlockFragment: st.encodeHeader(":method", "POST"),
		EndStream:     false,
		EndHeaders:    true,
	})

	st.writeData(id, true, nil)
	st.wantHeaders(wantHeader{
		streamID:  1,
		endStream: false,
	})

	var pendingWindowUpdate = uint32(0)

	for i := 0; i < b.N; i += 1 {
		expected := nextMsg(i)
		st.wantData(wantData{
			streamID:  1,
			endStream: false,
			data:      expected,
		})
		// try to send infrequent but large window updates so they don't overwhelm the test
		pendingWindowUpdate += uint32(len(expected))
		if pendingWindowUpdate >= windowSize/2 {
			if err := st.fr.WriteWindowUpdate(0, pendingWindowUpdate); err != nil {
				b.Fatal(err)
			}
			if err := st.fr.WriteWindowUpdate(id, pendingWindowUpdate); err != nil {
				b.Fatal(err)
			}
			pendingWindowUpdate = 0
		}
	}
	st.wantData(wantData{
		streamID:  1,
		endStream: true,
	})
}

// go-fuzz bug, originally reported at https://github.com/bradfitz/http2/issues/53
// Verify we don't hang.
func TestIssue53(t *testing.T) { synctestTest(t, testIssue53) }
func testIssue53(t testing.TB) {
	const data = "PRI * HTTP/2.0\r\n\r\nSM" +
		"\r\n\r\n\x00\x00\x00\x01\ainfinfin\ad"
	s := &http.Server{
		ErrorLog: log.New(io.MultiWriter(stderrv(), twriter{t: t}), "", log.LstdFlags),
		Handler: http.HandlerFunc(func(w http.ResponseWriter, req *http.Request) {
			w.Write([]byte("hello"))
		}),
	}
	s2 := &Server{
		MaxReadFrameSize:             1 << 16,
		PermitProhibitedCipherSuites: true,
	}
	c := &issue53Conn{[]byte(data), false, false}
	s2.ServeConn(c, &ServeConnOpts{BaseConfig: s})
	if !c.closed {
		t.Fatal("connection is not closed")
	}
}

type issue53Conn struct {
	data    []byte
	closed  bool
	written bool
}

func (c *issue53Conn) Read(b []byte) (n int, err error) {
	if len(c.data) == 0 {
		return 0, io.EOF
	}
	n = copy(b, c.data)
	c.data = c.data[n:]
	return
}

func (c *issue53Conn) Write(b []byte) (n int, err error) {
	c.written = true
	return len(b), nil
}

func (c *issue53Conn) Close() error {
	c.closed = true
	return nil
}

func (c *issue53Conn) LocalAddr() net.Addr {
	return &net.TCPAddr{IP: net.IPv4(127, 0, 0, 1), Port: 49706}
}
func (c *issue53Conn) RemoteAddr() net.Addr {
	return &net.TCPAddr{IP: net.IPv4(127, 0, 0, 1), Port: 49706}
}
func (c *issue53Conn) SetDeadline(t time.Time) error      { return nil }
func (c *issue53Conn) SetReadDeadline(t time.Time) error  { return nil }
func (c *issue53Conn) SetWriteDeadline(t time.Time) error { return nil }

// TestServeConnNilOpts ensures that Server.ServeConn(conn, nil) works.
//
// golang.org/issue/33839
func TestServeConnNilOpts(t *testing.T) { synctestTest(t, testServeConnNilOpts) }
func testServeConnNilOpts(t testing.TB) {
	// A nil ServeConnOpts uses http.DefaultServeMux as the handler.
	var gotRequest string
	var mux http.ServeMux
	mux.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) {
		gotRequest = r.URL.Path
	})
	SetForTest(t, &http.DefaultServeMux, &mux)

	srvConn, cliConn := net.Pipe()
	defer srvConn.Close()
	defer cliConn.Close()

	s2 := &Server{}
	go s2.ServeConn(srvConn, nil)

	fr := NewFramer(cliConn, cliConn)
	io.WriteString(cliConn, ClientPreface)
	fr.WriteSettings()
	fr.WriteSettingsAck()
	var henc hpackEncoder
	const reqPath = "/request"
	fr.WriteHeaders(HeadersFrameParam{
		StreamID: 1,
		BlockFragment: henc.encodeHeaderRaw(t,
			":method", "GET",
			":path", reqPath,
			":scheme", "https",
			":authority", "foo.com",
		),
		EndStream:  true,
		EndHeaders: true,
	})

	synctest.Wait()
	if got, want := gotRequest, reqPath; got != want {
		t.Errorf("got request: %q, want %q", got, want)
	}
}

// golang.org/issue/12895
func TestConfigureServer(t *testing.T) { synctestTest(t, testConfigureServer) }
func testConfigureServer(t testing.TB) {
	tests := []struct {
		name      string
		tlsConfig *tls.Config
		wantErr   string
	}{
		{
			name: "empty server",
		},
		{
			name:      "empty CipherSuites",
			tlsConfig: &tls.Config{},
		},
		{
			name: "bad CipherSuites but MinVersion TLS 1.3",
			tlsConfig: &tls.Config{
				MinVersion:   tls.VersionTLS13,
				CipherSuites: []uint16{tls.TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384},
			},
		},
		{
			name: "just the required cipher suite",
			tlsConfig: &tls.Config{
				CipherSuites: []uint16{tls.TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256},
			},
		},
		{
			name: "just the alternative required cipher suite",
			tlsConfig: &tls.Config{
				CipherSuites: []uint16{tls.TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256},
			},
		},
		{
			name: "missing required cipher suite",
			tlsConfig: &tls.Config{
				CipherSuites: []uint16{tls.TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384},
			},
			wantErr: "is missing an HTTP/2-required",
		},
		{
			name: "required after bad",
			tlsConfig: &tls.Config{
				CipherSuites: []uint16{tls.TLS_RSA_WITH_RC4_128_SHA, tls.TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256},
			},
		},
		{
			name: "bad after required",
			tlsConfig: &tls.Config{
				CipherSuites: []uint16{tls.TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256, tls.TLS_RSA_WITH_RC4_128_SHA},
			},
		},
	}
	for _, tt := range tests {
		srv := &http.Server{TLSConfig: tt.tlsConfig}
		err := ConfigureServer(srv, nil)
		if (err != nil) != (tt.wantErr != "") {
			if tt.wantErr != "" {
				t.Errorf("%s: success, but want error", tt.name)
			} else {
				t.Errorf("%s: unexpected error: %v", tt.name, err)
			}
		}
		if err != nil && tt.wantErr != "" && !strings.Contains(err.Error(), tt.wantErr) {
			t.Errorf("%s: err = %v; want substring %q", tt.name, err, tt.wantErr)
		}
		if err == nil && !srv.TLSConfig.PreferServerCipherSuites {
			t.Errorf("%s: PreferServerCipherSuite is false; want true", tt.name)
		}
	}
}

func TestServerNoAutoContentLengthOnHead(t *testing.T) {
	synctestTest(t, testServerNoAutoContentLengthOnHead)
}
func testServerNoAutoContentLengthOnHead(t testing.TB) {
	st := newServerTester(t, func(w http.ResponseWriter, r *http.Request) {
		// No response body. (or smaller than one frame)
	})
	defer st.Close()
	st.greet()
	st.writeHeaders(HeadersFrameParam{
		StreamID:      1, // clients send odd numbers
		BlockFragment: st.encodeHeader(":method", "HEAD"),
		EndStream:     true,
		EndHeaders:    true,
	})
	st.wantHeaders(wantHeader{
		streamID:  1,
		endStream: true,
		header: http.Header{
			":status": []string{"200"},
		},
	})
}

// golang.org/issue/13495
func TestServerNoDuplicateContentType(t *testing.T) {
	synctestTest(t, testServerNoDuplicateContentType)
}
func testServerNoDuplicateContentType(t testing.TB) {
	st := newServerTester(t, func(w http.ResponseWriter, r *http.Request) {
		w.Header()["Content-Type"] = []string{""}
		fmt.Fprintf(w, "<html><head></head><body>hi</body></html>")
	})
	defer st.Close()
	st.greet()
	st.writeHeaders(HeadersFrameParam{
		StreamID:      1,
		BlockFragment: st.encodeHeader(),
		EndStream:     true,
		EndHeaders:    true,
	})
	st.wantHeaders(wantHeader{
		streamID:  1,
		endStream: false,
		header: http.Header{
			":status":        []string{"200"},
			"content-type":   []string{""},
			"content-length": []string{"41"},
		},
	})
}

func TestServerContentLengthCanBeDisabled(t *testing.T) {
	synctestTest(t, testServerContentLengthCanBeDisabled)
}
func testServerContentLengthCanBeDisabled(t testing.TB) {
	st := newServerTester(t, func(w http.ResponseWriter, r *http.Request) {
		w.Header()["Content-Length"] = nil
		fmt.Fprintf(w, "OK")
	})
	defer st.Close()
	st.greet()
	st.writeHeaders(HeadersFrameParam{
		StreamID:      1,
		BlockFragment: st.encodeHeader(),
		EndStream:     true,
		EndHeaders:    true,
	})
	st.wantHeaders(wantHeader{
		streamID:  1,
		endStream: false,
		header: http.Header{
			":status":      []string{"200"},
			"content-type": []string{"text/plain; charset=utf-8"},
		},
	})
}

func BenchmarkServer_GetRequest(b *testing.B) {
	DisableGoroutineTracking(b)
	b.ReportAllocs()
	const msg = "Hello, world."
	st := newServerTesterWithRealConn(b, func(w http.ResponseWriter, r *http.Request) {
		n, err := io.Copy(io.Discard, r.Body)
		if err != nil || n > 0 {
			b.Errorf("Read %d bytes, error %v; want 0 bytes.", n, err)
		}
		io.WriteString(w, msg)
	})
	defer st.Close()

	st.greet()
	// Give the server quota to reply. (plus it has the 64KB)
	if err := st.fr.WriteWindowUpdate(0, uint32(b.N*len(msg))); err != nil {
		b.Fatal(err)
	}
	hbf := st.encodeHeader(":method", "GET")
	for i := 0; i < b.N; i++ {
		streamID := uint32(1 + 2*i)
		st.writeHeaders(HeadersFrameParam{
			StreamID:      streamID,
			BlockFragment: hbf,
			EndStream:     true,
			EndHeaders:    true,
		})
		st.wantFrameType(FrameHeaders)
		st.wantFrameType(FrameData)
	}
}

func BenchmarkServer_PostRequest(b *testing.B) {
	DisableGoroutineTracking(b)
	b.ReportAllocs()
	const msg = "Hello, world."
	st := newServerTesterWithRealConn(b, func(w http.ResponseWriter, r *http.Request) {
		n, err := io.Copy(io.Discard, r.Body)
		if err != nil || n > 0 {
			b.Errorf("Read %d bytes, error %v; want 0 bytes.", n, err)
		}
		io.WriteString(w, msg)
	})
	defer st.Close()
	st.greet()
	// Give the server quota to reply. (plus it has the 64KB)
	if err := st.fr.WriteWindowUpdate(0, uint32(b.N*len(msg))); err != nil {
		b.Fatal(err)
	}
	hbf := st.encodeHeader(":method", "POST")
	for i := 0; i < b.N; i++ {
		streamID := uint32(1 + 2*i)
		st.writeHeaders(HeadersFrameParam{
			StreamID:      streamID,
			BlockFragment: hbf,
			EndStream:     false,
			EndHeaders:    true,
		})
		st.writeData(streamID, true, nil)
		st.wantFrameType(FrameHeaders)
		st.wantFrameType(FrameData)
	}
}

type connStateConn struct {
	net.Conn
	cs tls.ConnectionState
}

func (c connStateConn) ConnectionState() tls.ConnectionState { return c.cs }

// golang.org/issue/12737 -- handle any net.Conn, not just
// *tls.Conn.
func TestServerHandleCustomConn(t *testing.T) { synctestTest(t, testServerHandleCustomConn) }
func testServerHandleCustomConn(t testing.TB) {
	var s Server
	c1, c2 := net.Pipe()
	clientDone := make(chan struct{})
	handlerDone := make(chan struct{})
	var req *http.Request
	go func() {
		defer close(clientDone)
		defer c2.Close()
		fr := NewFramer(c2, c2)
		io.WriteString(c2, ClientPreface)
		fr.WriteSettings()
		fr.WriteSettingsAck()
		f, err := fr.ReadFrame()
		if err != nil {
			t.Error(err)
			return
		}
		if sf, ok := f.(*SettingsFrame); !ok || sf.IsAck() {
			t.Errorf("Got %v; want non-ACK SettingsFrame", SummarizeFrame(f))
			return
		}
		f, err = fr.ReadFrame()
		if err != nil {
			t.Error(err)
			return
		}
		if sf, ok := f.(*SettingsFrame); !ok || !sf.IsAck() {
			t.Errorf("Got %v; want ACK SettingsFrame", SummarizeFrame(f))
			return
		}
		var henc hpackEncoder
		fr.WriteHeaders(HeadersFrameParam{
			StreamID:      1,
			BlockFragment: henc.encodeHeaderRaw(t, ":method", "GET", ":path", "/", ":scheme", "https", ":authority", "foo.com"),
			EndStream:     true,
			EndHeaders:    true,
		})
		go io.Copy(io.Discard, c2)
		<-handlerDone
	}()
	const testString = "my custom ConnectionState"
	const cipher_TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256 = 0xC02F // defined in ciphers.go
	fakeConnState := tls.ConnectionState{
		ServerName:  testString,
		Version:     tls.VersionTLS12,
		CipherSuite: cipher_TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256,
	}
	go s.ServeConn(connStateConn{c1, fakeConnState}, &ServeConnOpts{
		BaseConfig: &http.Server{
			Handler: http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
				defer close(handlerDone)
				req = r
			}),
		}})
	<-clientDone

	if req.TLS == nil {
		t.Fatalf("Request.TLS is nil. Got: %#v", req)
	}
	if req.TLS.ServerName != testString {
		t.Fatalf("Request.TLS = %+v; want ServerName of %q", req.TLS, testString)
	}
}

// golang.org/issue/14214
func TestServer_Rejects_ConnHeaders(t *testing.T) { synctestTest(t, testServer_Rejects_ConnHeaders) }
func testServer_Rejects_ConnHeaders(t testing.TB) {
	st := newServerTester(t, func(w http.ResponseWriter, r *http.Request) {
		t.Error("should not get to Handler")
	})
	defer st.Close()
	st.greet()
	st.bodylessReq1("connection", "foo")
	st.wantHeaders(wantHeader{
		streamID:  1,
		endStream: false,
		header: http.Header{
			":status":                []string{"400"},
			"content-type":           []string{"text/plain; charset=utf-8"},
			"x-content-type-options": []string{"nosniff"},
			"content-length":         []string{"51"},
		},
	})
}

type hpackEncoder struct {
	enc *hpack.Encoder
	buf bytes.Buffer
}

func (he *hpackEncoder) encodeHeaderRaw(t testing.TB, headers ...string) []byte {
	if len(headers)%2 == 1 {
		panic("odd number of kv args")
	}
	he.buf.Reset()
	if he.enc == nil {
		he.enc = hpack.NewEncoder(&he.buf)
	}
	for len(headers) > 0 {
		k, v := headers[0], headers[1]
		err := he.enc.WriteField(hpack.HeaderField{Name: k, Value: v})
		if err != nil {
			t.Fatalf("HPACK encoding error for %q/%q: %v", k, v, err)
		}
		headers = headers[2:]
	}
	return he.buf.Bytes()
}

// golang.org/issue/14030
func TestExpect100ContinueAfterHandlerWrites(t *testing.T) {
	synctestTest(t, testExpect100ContinueAfterHandlerWrites)
}
func testExpect100ContinueAfterHandlerWrites(t testing.TB) {
	const msg = "Hello"
	const msg2 = "World"

	doRead := make(chan bool, 1)
	defer close(doRead) // fallback cleanup

	ts := newTestServer(t, func(w http.ResponseWriter, r *http.Request) {
		io.WriteString(w, msg)
		w.(http.Flusher).Flush()

		// Do a read, which might force a 100-continue status to be sent.
		<-doRead
		r.Body.Read(make([]byte, 10))

		io.WriteString(w, msg2)
	})

	tr := &Transport{TLSClientConfig: tlsConfigInsecure}
	defer tr.CloseIdleConnections()

	req, _ := http.NewRequest("POST", ts.URL, io.LimitReader(neverEnding('A'), 2<<20))
	req.Header.Set("Expect", "100-continue")

	res, err := tr.RoundTrip(req)
	if err != nil {
		t.Fatal(err)
	}
	defer res.Body.Close()

	buf := make([]byte, len(msg))
	if _, err := io.ReadFull(res.Body, buf); err != nil {
		t.Fatal(err)
	}
	if string(buf) != msg {
		t.Fatalf("msg = %q; want %q", buf, msg)
	}

	doRead <- true

	if _, err := io.ReadFull(res.Body, buf); err != nil {
		t.Fatal(err)
	}
	if string(buf) != msg2 {
		t.Fatalf("second msg = %q; want %q", buf, msg2)
	}
}

type funcReader func([]byte) (n int, err error)

func (f funcReader) Read(p []byte) (n int, err error) { return f(p) }

// golang.org/issue/16481 -- return flow control when streams close with unread data.
// (The Server version of the bug. See also TestUnreadFlowControlReturned_Transport)
func TestUnreadFlowControlReturned_Server(t *testing.T) {
	for _, tt := range []struct {
		name  string
		reqFn func(r *http.Request)
	}{
		{
			"body-open",
			func(r *http.Request) {},
		},
		{
			"body-closed",
			func(r *http.Request) {
				r.Body.Close()
			},
		},
		{
			"read-1-byte-and-close",
			func(r *http.Request) {
				b := make([]byte, 1)
				r.Body.Read(b)
				r.Body.Close()
			},
		},
	} {
		synctestSubtest(t, tt.name, func(t testing.TB) {
			unblock := make(chan bool, 1)
			defer close(unblock)

			ts := newTestServer(t, func(w http.ResponseWriter, r *http.Request) {
				// Don't read the 16KB request body. Wait until the client's
				// done sending it and then return. This should cause the Server
				// to then return those 16KB of flow control to the client.
				tt.reqFn(r)
				<-unblock
			})

			tr := &Transport{TLSClientConfig: tlsConfigInsecure}
			defer tr.CloseIdleConnections()

			// This previously hung on the 4th iteration.
			iters := 100
			if testing.Short() {
				iters = 20
			}
			for i := 0; i < iters; i++ {
				body := io.MultiReader(
					io.LimitReader(neverEnding('A'), 16<<10),
					funcReader(func([]byte) (n int, err error) {
						unblock <- true
						return 0, io.EOF
					}),
				)
				req, _ := http.NewRequest("POST", ts.URL, body)
				res, err := tr.RoundTrip(req)
				if err != nil {
					t.Fatal(tt.name, err)
				}
				res.Body.Close()
			}
		})
	}
}

func TestServerReturnsStreamAndConnFlowControlOnBodyClose(t *testing.T) {
	synctestTest(t, testServerReturnsStreamAndConnFlowControlOnBodyClose)
}
func testServerReturnsStreamAndConnFlowControlOnBodyClose(t testing.TB) {
	unblockHandler := make(chan struct{})
	defer close(unblockHandler)

	st := newServerTester(t, func(w http.ResponseWriter, r *http.Request) {
		r.Body.Close()
		w.WriteHeader(200)
		w.(http.Flusher).Flush()
		<-unblockHandler
	})
	defer st.Close()

	st.greet()
	st.writeHeaders(HeadersFrameParam{
		StreamID:      1,
		BlockFragment: st.encodeHeader(),
		EndHeaders:    true,
	})
	st.wantHeaders(wantHeader{
		streamID:  1,
		endStream: false,
	})
	const size = InflowMinRefresh // enough to trigger flow control return
	st.writeData(1, false, make([]byte, size))
	st.wantWindowUpdate(0, size) // conn-level flow control is returned
	unblockHandler <- struct{}{}
	st.wantData(wantData{
		streamID:  1,
		endStream: true,
	})
}

func TestServerIdleTimeout(t *testing.T) { synctestTest(t, testServerIdleTimeout) }
func testServerIdleTimeout(t testing.TB) {
	if testing.Short() {
		t.Skip("skipping in short mode")
	}

	st := newServerTester(t, func(w http.ResponseWriter, r *http.Request) {
	}, func(h2s *Server) {
		h2s.IdleTimeout = 500 * time.Millisecond
	})
	defer st.Close()

	st.greet()
	st.advance(500 * time.Millisecond)
	st.wantGoAway(0, ErrCodeNo)
}

func TestServerIdleTimeout_AfterRequest(t *testing.T) {
	synctestTest(t, testServerIdleTimeout_AfterRequest)
}
func testServerIdleTimeout_AfterRequest(t testing.TB) {
	if testing.Short() {
		t.Skip("skipping in short mode")
	}
	const (
		requestTimeout = 2 * time.Second
		idleTimeout    = 1 * time.Second
	)

	var st *serverTester
	st = newServerTester(t, func(w http.ResponseWriter, r *http.Request) {
		time.Sleep(requestTimeout)
	}, func(h2s *Server) {
		h2s.IdleTimeout = idleTimeout
	})
	defer st.Close()

	st.greet()

	// Send a request which takes twice the timeout. Verifies the
	// idle timeout doesn't fire while we're in a request:
	st.bodylessReq1()
	st.advance(requestTimeout)
	st.wantHeaders(wantHeader{
		streamID:  1,
		endStream: true,
	})

	// But the idle timeout should be rearmed after the request
	// is done:
	st.advance(idleTimeout)
	st.wantGoAway(1, ErrCodeNo)
}

// grpc-go closes the Request.Body currently with a Read.
// Verify that it doesn't race.
// See https://github.com/grpc/grpc-go/pull/938
func TestRequestBodyReadCloseRace(t *testing.T) { synctestTest(t, testRequestBodyReadCloseRace) }
func testRequestBodyReadCloseRace(t testing.TB) {
	st := newServerTester(t, func(w http.ResponseWriter, r *http.Request) {
		go r.Body.Close()
		io.Copy(io.Discard, r.Body)
	})
	st.greet()

	data := make([]byte, 1024)
	for i := range 100 {
		streamID := uint32(1 + (i * 2)) // clients send odd numbers
		st.writeHeaders(HeadersFrameParam{
			StreamID:      streamID,
			BlockFragment: st.encodeHeader(),
			EndHeaders:    true,
		})
		st.writeData(1, false, data)

		for {
			// Look for a RST_STREAM frame.
			// Skip over anything else (HEADERS and WINDOW_UPDATE).
			fr := st.readFrame()
			if fr == nil {
				t.Fatalf("got no RSTStreamFrame, want one")
			}
			rst, ok := fr.(*RSTStreamFrame)
			if !ok {
				continue
			}
			// We can get NO or STREAM_CLOSED depending on scheduling.
			if rst.ErrCode != ErrCodeNo && rst.ErrCode != ErrCodeStreamClosed {
				t.Fatalf("got RSTStreamFrame with error code %v, want ErrCodeNo or ErrCodeStreamClosed", rst.ErrCode)
			}
			break
		}
	}
}

func TestIssue20704Race(t *testing.T) { synctestTest(t, testIssue20704Race) }
func testIssue20704Race(t testing.TB) {
	if testing.Short() && os.Getenv("GO_BUILDER_NAME") == "" {
		t.Skip("skipping in short mode")
	}
	const (
		itemSize  = 1 << 10
		itemCount = 100
	)

	ts := newTestServer(t, func(w http.ResponseWriter, r *http.Request) {
		for i := 0; i < itemCount; i++ {
			_, err := w.Write(make([]byte, itemSize))
			if err != nil {
				return
			}
		}
	})

	tr := &Transport{TLSClientConfig: tlsConfigInsecure}
	defer tr.CloseIdleConnections()
	cl := &http.Client{Transport: tr}

	for i := 0; i < 1000; i++ {
		resp, err := cl.Get(ts.URL)
		if err != nil {
			t.Fatal(err)
		}
		// Force a RST stream to the server by closing without
		// reading the body:
		resp.Body.Close()
	}
}

func TestServer_Rejects_TooSmall(t *testing.T) { synctestTest(t, testServer_Rejects_TooSmall) }
func testServer_Rejects_TooSmall(t testing.TB) {
	testServerResponse(t, func(w http.ResponseWriter, r *http.Request) error {
		io.ReadAll(r.Body)
		return nil
	}, func(st *serverTester) {
		st.writeHeaders(HeadersFrameParam{
			StreamID: 1, // clients send odd numbers
			BlockFragment: st.encodeHeader(
				":method", "POST",
				"content-length", "4",
			),
			EndStream:  false, // to say DATA frames are coming
			EndHeaders: true,
		})
		st.writeData(1, true, []byte("12345"))
		st.wantRSTStream(1, ErrCodeProtocol)
		st.wantConnFlowControlConsumed(0)
	})
}

// Tests that a handler setting "Connection: close" results in a GOAWAY being sent,
// and the connection still completing.
func TestServerHandlerConnectionClose(t *testing.T) {
	synctestTest(t, testServerHandlerConnectionClose)
}
func testServerHandlerConnectionClose(t testing.TB) {
	unblockHandler := make(chan bool, 1)
	testServerResponse(t, func(w http.ResponseWriter, r *http.Request) error {
		w.Header().Set("Connection", "close")
		w.Header().Set("Foo", "bar")
		w.(http.Flusher).Flush()
		<-unblockHandler
		return nil
	}, func(st *serverTester) {
		defer close(unblockHandler) // backup; in case of errors
		st.writeHeaders(HeadersFrameParam{
			StreamID:      1,
			BlockFragment: st.encodeHeader(),
			EndStream:     true,
			EndHeaders:    true,
		})
		var sawGoAway bool
		var sawRes bool
		var sawWindowUpdate bool
		for {
			f := st.readFrame()
			if f == nil {
				break
			}
			switch f := f.(type) {
			case *GoAwayFrame:
				sawGoAway = true
				if f.LastStreamID != 1 || f.ErrCode != ErrCodeNo {
					t.Errorf("unexpected GOAWAY frame: %v", SummarizeFrame(f))
				}
				// Create a stream and reset it.
				// The server should ignore the stream.
				st.writeHeaders(HeadersFrameParam{
					StreamID:      3,
					BlockFragment: st.encodeHeader(),
					EndStream:     false,
					EndHeaders:    true,
				})
				st.fr.WriteRSTStream(3, ErrCodeCancel)
				// Create a stream and send data to it.
				// The server should return flow control, even though it
				// does not process the stream.
				st.writeHeaders(HeadersFrameParam{
					StreamID:      5,
					BlockFragment: st.encodeHeader(),
					EndStream:     false,
					EndHeaders:    true,
				})
				// Write enough data to trigger a window update.
				st.writeData(5, true, make([]byte, 1<<19))
			case *HeadersFrame:
				goth := st.decodeHeader(f.HeaderBlockFragment())
				wanth := [][2]string{
					{":status", "200"},
					{"foo", "bar"},
				}
				if !reflect.DeepEqual(goth, wanth) {
					t.Errorf("got headers %v; want %v", goth, wanth)
				}
				sawRes = true
			case *DataFrame:
				if f.StreamID != 1 || !f.StreamEnded() || len(f.Data()) != 0 {
					t.Errorf("unexpected DATA frame: %v", SummarizeFrame(f))
				}
			case *WindowUpdateFrame:
				if !sawGoAway {
					t.Errorf("unexpected WINDOW_UPDATE frame: %v", SummarizeFrame(f))
					return
				}
				if f.StreamID != 0 {
					st.t.Fatalf("WindowUpdate StreamID = %d; want 5", f.FrameHeader.StreamID)
					return
				}
				sawWindowUpdate = true
				unblockHandler <- true
				st.sync()
				st.advance(GoAwayTimeout)
			default:
				t.Logf("unexpected frame: %v", SummarizeFrame(f))
			}
		}
		if !sawGoAway {
			t.Errorf("didn't see GOAWAY")
		}
		if !sawRes {
			t.Errorf("didn't see response")
		}
		if !sawWindowUpdate {
			t.Errorf("didn't see WINDOW_UPDATE")
		}
	})
}

func TestServer_Headers_HalfCloseRemote(t *testing.T) {
	synctestTest(t, testServer_Headers_HalfCloseRemote)
}
func testServer_Headers_HalfCloseRemote(t testing.TB) {
	var st *serverTester
	writeData := make(chan bool)
	writeHeaders := make(chan bool)
	leaveHandler := make(chan bool)
	st = newServerTester(t, func(w http.ResponseWriter, r *http.Request) {
		if !st.streamExists(1) {
			t.Errorf("stream 1 does not exist in handler")
		}
		if got, want := st.streamState(1), StateOpen; got != want {
			t.Errorf("in handler, state is %v; want %v", got, want)
		}
		writeData <- true
		if n, err := r.Body.Read(make([]byte, 1)); n != 0 || err != io.EOF {
			t.Errorf("body read = %d, %v; want 0, EOF", n, err)
		}
		if got, want := st.streamState(1), StateHalfClosedRemote; got != want {
			t.Errorf("in handler, state is %v; want %v", got, want)
		}
		writeHeaders <- true

		<-leaveHandler
	})
	st.greet()

	st.writeHeaders(HeadersFrameParam{
		StreamID:      1,
		BlockFragment: st.encodeHeader(),
		EndStream:     false, // keep it open
		EndHeaders:    true,
	})
	<-writeData
	st.writeData(1, true, nil)

	<-writeHeaders

	st.writeHeaders(HeadersFrameParam{
		StreamID:      1,
		BlockFragment: st.encodeHeader(),
		EndStream:     false, // keep it open
		EndHeaders:    true,
	})

	defer close(leaveHandler)

	st.wantRSTStream(1, ErrCodeStreamClosed)
}

func TestServerGracefulShutdown(t *testing.T) { synctestTest(t, testServerGracefulShutdown) }
func testServerGracefulShutdown(t testing.TB) {
	handlerDone := make(chan struct{})
	st := newServerTester(t, func(w http.ResponseWriter, r *http.Request) {
		<-handlerDone
		w.Header().Set("x-foo", "bar")
	})
	defer st.Close()

	st.greet()
	st.bodylessReq1()

	st.sync()
	st.h1server.Shutdown(context.Background())

	st.wantGoAway(1, ErrCodeNo)

	close(handlerDone)
	st.sync()

	st.wantHeaders(wantHeader{
		streamID:  1,
		endStream: true,
		header: http.Header{
			":status":        []string{"200"},
			"x-foo":          []string{"bar"},
			"content-length": []string{"0"},
		},
	})

	n, err := st.cc.Read([]byte{0})
	if n != 0 || err == nil {
		t.Errorf("Read = %v, %v; want 0, non-nil", n, err)
	}
}

// Issue 31753: don't sniff when Content-Encoding is set
func TestContentEncodingNoSniffing(t *testing.T) {
	type resp struct {
		name string
		body []byte
		// setting Content-Encoding as an interface instead of a string
		// directly, so as to differentiate between 3 states:
		//    unset, empty string "" and set string "foo/bar".
		contentEncoding interface{}
		wantContentType string
	}

	resps := []*resp{
		{
			name:            "gzip content-encoding, gzipped", // don't sniff.
			contentEncoding: "application/gzip",
			wantContentType: "",
			body: func() []byte {
				buf := new(bytes.Buffer)
				gzw := gzip.NewWriter(buf)
				gzw.Write([]byte("doctype html><p>Hello</p>"))
				gzw.Close()
				return buf.Bytes()
			}(),
		},
		{
			name:            "zlib content-encoding, zlibbed", // don't sniff.
			contentEncoding: "application/zlib",
			wantContentType: "",
			body: func() []byte {
				buf := new(bytes.Buffer)
				zw := zlib.NewWriter(buf)
				zw.Write([]byte("doctype html><p>Hello</p>"))
				zw.Close()
				return buf.Bytes()
			}(),
		},
		{
			name:            "no content-encoding", // must sniff.
			wantContentType: "application/x-gzip",
			body: func() []byte {
				buf := new(bytes.Buffer)
				gzw := gzip.NewWriter(buf)
				gzw.Write([]byte("doctype html><p>Hello</p>"))
				gzw.Close()
				return buf.Bytes()
			}(),
		},
		{
			name:            "phony content-encoding", // don't sniff.
			contentEncoding: "foo/bar",
			body:            []byte("doctype html><p>Hello</p>"),
		},
		{
			name:            "empty but set content-encoding",
			contentEncoding: "",
			wantContentType: "audio/mpeg",
			body:            []byte("ID3"),
		},
	}

	for _, tt := range resps {
		synctestSubtest(t, tt.name, func(t testing.TB) {
			ts := newTestServer(t, func(w http.ResponseWriter, r *http.Request) {
				if tt.contentEncoding != nil {
					w.Header().Set("Content-Encoding", tt.contentEncoding.(string))
				}
				w.Write(tt.body)
			})

			tr := &Transport{TLSClientConfig: tlsConfigInsecure}
			defer tr.CloseIdleConnections()

			req, _ := http.NewRequest("GET", ts.URL, nil)
			res, err := tr.RoundTrip(req)
			if err != nil {
				t.Fatalf("GET %s: %v", ts.URL, err)
			}
			defer res.Body.Close()

			g := res.Header.Get("Content-Encoding")
			t.Logf("%s: Content-Encoding: %s", ts.URL, g)

			if w := tt.contentEncoding; g != w {
				if w != nil { // The case where contentEncoding was set explicitly.
					t.Errorf("Content-Encoding mismatch\n\tgot:  %q\n\twant: %q", g, w)
				} else if g != "" { // "" should be the equivalent when the contentEncoding is unset.
					t.Errorf("Unexpected Content-Encoding %q", g)
				}
			}

			g = res.Header.Get("Content-Type")
			if w := tt.wantContentType; g != w {
				t.Errorf("Content-Type mismatch\n\tgot:  %q\n\twant: %q", g, w)
			}
			t.Logf("%s: Content-Type: %s", ts.URL, g)
		})
	}
}

func TestServerWindowUpdateOnBodyClose(t *testing.T) {
	synctestTest(t, testServerWindowUpdateOnBodyClose)
}
func testServerWindowUpdateOnBodyClose(t testing.TB) {
	const windowSize = 65535 * 2
	content := make([]byte, windowSize)
	errc := make(chan error)
	st := newServerTester(t, func(w http.ResponseWriter, r *http.Request) {
		buf := make([]byte, 4)
		n, err := io.ReadFull(r.Body, buf)
		if err != nil {
			errc <- err
			return
		}
		if n != len(buf) {
			errc <- fmt.Errorf("too few bytes read: %d", n)
			return
		}
		r.Body.Close()
		errc <- nil
	}, func(s *Server) {
		s.MaxUploadBufferPerConnection = windowSize
		s.MaxUploadBufferPerStream = windowSize
	})
	defer st.Close()

	st.greet()
	st.writeHeaders(HeadersFrameParam{
		StreamID: 1, // clients send odd numbers
		BlockFragment: st.encodeHeader(
			":method", "POST",
			"content-length", strconv.Itoa(len(content)),
		),
		EndStream:  false, // to say DATA frames are coming
		EndHeaders: true,
	})
	st.writeData(1, false, content[:windowSize/2])
	if err := <-errc; err != nil {
		t.Fatal(err)
	}

	// Wait for flow control credit for the portion of the request written so far.
	increments := windowSize / 2
	for {
		f := st.readFrame()
		if f == nil {
			break
		}
		if wu, ok := f.(*WindowUpdateFrame); ok && wu.StreamID == 0 {
			increments -= int(wu.Increment)
			if increments == 0 {
				break
			}
		}
	}

	// Writing data after the stream is reset immediately returns flow control credit.
	st.writeData(1, false, content[windowSize/2:])
	st.wantWindowUpdate(0, windowSize/2)
}

func TestNoErrorLoggedOnPostAfterGOAWAY(t *testing.T) {
	synctestTest(t, testNoErrorLoggedOnPostAfterGOAWAY)
}
func testNoErrorLoggedOnPostAfterGOAWAY(t testing.TB) {
	st := newServerTester(t, func(w http.ResponseWriter, r *http.Request) {})
	defer st.Close()

	st.greet()

	content := "some content"
	st.writeHeaders(HeadersFrameParam{
		StreamID: 1,
		BlockFragment: st.encodeHeader(
			":method", "POST",
			"content-length", strconv.Itoa(len(content)),
		),
		EndStream:  false,
		EndHeaders: true,
	})
	st.wantHeaders(wantHeader{
		streamID:  1,
		endStream: true,
	})

	st.sc.StartGracefulShutdown()
	st.wantRSTStream(1, ErrCodeNo)
	st.wantGoAway(1, ErrCodeNo)

	st.writeData(1, true, []byte(content))
	st.Close()

	if bytes.Contains(st.serverLogBuf.Bytes(), []byte("PROTOCOL_ERROR")) {
		t.Error("got protocol error")
	}
}

func TestServerSendsProcessing(t *testing.T) { synctestTest(t, testServerSendsProcessing) }
func testServerSendsProcessing(t testing.TB) {
	testServerResponse(t, func(w http.ResponseWriter, r *http.Request) error {
		w.WriteHeader(http.StatusProcessing)
		w.Write([]byte("stuff"))

		return nil
	}, func(st *serverTester) {
		getSlash(st)
		st.wantHeaders(wantHeader{
			streamID:  1,
			endStream: false,
			header: http.Header{
				":status": []string{"102"},
			},
		})
		st.wantHeaders(wantHeader{
			streamID:  1,
			endStream: false,
			header: http.Header{
				":status":        []string{"200"},
				"content-type":   []string{"text/plain; charset=utf-8"},
				"content-length": []string{"5"},
			},
		})
	})
}

func TestServerSendsEarlyHints(t *testing.T) { synctestTest(t, testServerSendsEarlyHints) }
func testServerSendsEarlyHints(t testing.TB) {
	testServerResponse(t, func(w http.ResponseWriter, r *http.Request) error {
		h := w.Header()
		h.Add("Content-Length", "123")
		h.Add("Link", "</style.css>; rel=preload; as=style")
		h.Add("Link", "</script.js>; rel=preload; as=script")
		w.WriteHeader(http.StatusEarlyHints)

		h.Add("Link", "</foo.js>; rel=preload; as=script")
		w.WriteHeader(http.StatusEarlyHints)

		w.Write([]byte("stuff"))

		return nil
	}, func(st *serverTester) {
		getSlash(st)
		st.wantHeaders(wantHeader{
			streamID:  1,
			endStream: false,
			header: http.Header{
				":status": []string{"103"},
				"link": []string{
					"</style.css>; rel=preload; as=style",
					"</script.js>; rel=preload; as=script",
				},
			},
		})
		st.wantHeaders(wantHeader{
			streamID:  1,
			endStream: false,
			header: http.Header{
				":status": []string{"103"},
				"link": []string{
					"</style.css>; rel=preload; as=style",
					"</script.js>; rel=preload; as=script",
					"</foo.js>; rel=preload; as=script",
				},
			},
		})
		st.wantHeaders(wantHeader{
			streamID:  1,
			endStream: false,
			header: http.Header{
				":status": []string{"200"},
				"link": []string{
					"</style.css>; rel=preload; as=style",
					"</script.js>; rel=preload; as=script",
					"</foo.js>; rel=preload; as=script",
				},
				"content-type":   []string{"text/plain; charset=utf-8"},
				"content-length": []string{"123"},
			},
		})
	})
}

func TestProtocolErrorAfterGoAway(t *testing.T) { synctestTest(t, testProtocolErrorAfterGoAway) }
func testProtocolErrorAfterGoAway(t testing.TB) {
	st := newServerTester(t, func(w http.ResponseWriter, r *http.Request) {
		io.Copy(io.Discard, r.Body)
	})
	defer st.Close()

	st.greet()
	content := "some content"
	st.writeHeaders(HeadersFrameParam{
		StreamID: 1,
		BlockFragment: st.encodeHeader(
			":method", "POST",
			"content-length", strconv.Itoa(len(content)),
		),
		EndStream:  false,
		EndHeaders: true,
	})
	st.writeData(1, false, []byte(content[:5]))

	// Send a GOAWAY with ErrCodeNo, followed by a bogus window update.
	// The server should close the connection.
	if err := st.fr.WriteGoAway(1, ErrCodeNo, nil); err != nil {
		t.Fatal(err)
	}
	if err := st.fr.WriteWindowUpdate(0, 1<<31-1); err != nil {
		t.Fatal(err)
	}

	st.advance(GoAwayTimeout)
	st.wantGoAway(1, ErrCodeNo)
	st.wantClosed()
}

func TestServerInitialFlowControlWindow(t *testing.T) {
	for _, want := range []int32{
		65535,
		1 << 19,
		1 << 21,
		// For MaxUploadBufferPerConnection values in the range
		// (65535, 65535*2), we don't send an initial WINDOW_UPDATE
		// because we only send flow control when the window drops
		// below half of the maximum. Perhaps it would be nice to
		// test this case, but we currently do not.
		65535 * 2,
	} {
		synctestSubtest(t, fmt.Sprint(want), func(t testing.TB) {

			st := newServerTester(t, func(w http.ResponseWriter, r *http.Request) {
			}, func(s *Server) {
				s.MaxUploadBufferPerConnection = want
			})
			st.writePreface()
			st.writeSettings()
			_ = readFrame[*SettingsFrame](t, st)
			st.writeSettingsAck()
			st.writeHeaders(HeadersFrameParam{
				StreamID:      1,
				BlockFragment: st.encodeHeader(),
				EndStream:     true,
				EndHeaders:    true,
			})
			window := 65535
		Frames:
			for {
				f := st.readFrame()
				switch f := f.(type) {
				case *WindowUpdateFrame:
					if f.FrameHeader.StreamID != 0 {
						t.Errorf("WindowUpdate StreamID = %d; want 0", f.FrameHeader.StreamID)
						return
					}
					window += int(f.Increment)
				case *HeadersFrame:
					break Frames
				case nil:
					break Frames
				default:
				}
			}
			if window != int(want) {
				t.Errorf("got initial flow control window = %v, want %v", window, want)
			}
		})
	}
}

// TestServerWriteDoesNotRetainBufferAfterReturn checks for access to
// the slice passed to ResponseWriter.Write after Write returns.
//
// Terminating the request stream on the client causes Write to return.
// We should not access the slice after this point.
func TestServerWriteDoesNotRetainBufferAfterReturn(t *testing.T) {
	synctestTest(t, testServerWriteDoesNotRetainBufferAfterReturn)
}
func testServerWriteDoesNotRetainBufferAfterReturn(t testing.TB) {
	donec := make(chan struct{})
	ts := newTestServer(t, func(w http.ResponseWriter, r *http.Request) {
		defer close(donec)
		buf := make([]byte, 1<<20)
		var i byte
		for {
			i++
			_, err := w.Write(buf)
			for j := range buf {
				buf[j] = byte(i) // trigger race detector
			}
			if err != nil {
				return
			}
		}
	})

	tr := &Transport{TLSClientConfig: tlsConfigInsecure}
	defer tr.CloseIdleConnections()

	req, _ := http.NewRequest("GET", ts.URL, nil)
	res, err := tr.RoundTrip(req)
	if err != nil {
		t.Fatal(err)
	}
	res.Body.Close()
	<-donec
}

// TestServerWriteDoesNotRetainBufferAfterServerClose checks for access to
// the slice passed to ResponseWriter.Write after Write returns.
//
// Shutting down the Server causes Write to return.
// We should not access the slice after this point.
func TestServerWriteDoesNotRetainBufferAfterServerClose(t *testing.T) {
	synctestTest(t, testServerWriteDoesNotRetainBufferAfterServerClose)
}
func testServerWriteDoesNotRetainBufferAfterServerClose(t testing.TB) {
	donec := make(chan struct{}, 1)
	ts := newTestServer(t, func(w http.ResponseWriter, r *http.Request) {
		donec <- struct{}{}
		defer close(donec)
		buf := make([]byte, 1<<20)
		var i byte
		for {
			i++
			_, err := w.Write(buf)
			for j := range buf {
				buf[j] = byte(i)
			}
			if err != nil {
				return
			}
		}
	})

	tr := &Transport{TLSClientConfig: tlsConfigInsecure}
	defer tr.CloseIdleConnections()

	req, _ := http.NewRequest("GET", ts.URL, nil)
	res, err := tr.RoundTrip(req)
	if err != nil {
		t.Fatal(err)
	}
	defer res.Body.Close()
	<-donec
	ts.Config.Close()
	<-donec
}

func TestServerMaxHandlerGoroutines(t *testing.T) { synctestTest(t, testServerMaxHandlerGoroutines) }
func testServerMaxHandlerGoroutines(t testing.TB) {
	const maxHandlers = 10
	handlerc := make(chan chan bool)
	donec := make(chan struct{})
	defer close(donec)
	st := newServerTester(t, func(w http.ResponseWriter, r *http.Request) {
		stopc := make(chan bool, 1)
		select {
		case handlerc <- stopc:
		case <-donec:
		}
		select {
		case shouldPanic := <-stopc:
			if shouldPanic {
				panic(http.ErrAbortHandler)
			}
		case <-donec:
		}
	}, func(s *Server) {
		s.MaxConcurrentStreams = maxHandlers
	})
	defer st.Close()

	st.greet()

	// Make maxHandlers concurrent requests.
	// Reset them all, but only after the handler goroutines have started.
	var stops []chan bool
	streamID := uint32(1)
	for i := 0; i < maxHandlers; i++ {
		st.writeHeaders(HeadersFrameParam{
			StreamID:      streamID,
			BlockFragment: st.encodeHeader(),
			EndStream:     true,
			EndHeaders:    true,
		})
		stops = append(stops, <-handlerc)
		st.fr.WriteRSTStream(streamID, ErrCodeCancel)
		streamID += 2
	}

	// Start another request, and immediately reset it.
	st.writeHeaders(HeadersFrameParam{
		StreamID:      streamID,
		BlockFragment: st.encodeHeader(),
		EndStream:     true,
		EndHeaders:    true,
	})
	st.fr.WriteRSTStream(streamID, ErrCodeCancel)
	streamID += 2

	// Start another two requests. Don't reset these.
	for i := 0; i < 2; i++ {
		st.writeHeaders(HeadersFrameParam{
			StreamID:      streamID,
			BlockFragment: st.encodeHeader(),
			EndStream:     true,
			EndHeaders:    true,
		})
		streamID += 2
	}

	// The initial maxHandlers handlers are still executing,
	// so the last two requests don't start any new handlers.
	select {
	case <-handlerc:
		t.Errorf("handler unexpectedly started while maxHandlers are already running")
	case <-time.After(1 * time.Millisecond):
	}

	// Tell two handlers to exit.
	// The pending requests which weren't reset start handlers.
	stops[0] <- false // normal exit
	stops[1] <- true  // panic
	stops = stops[2:]
	stops = append(stops, <-handlerc)
	stops = append(stops, <-handlerc)

	// Make a bunch more requests.
	// Eventually, the server tells us to go away.
	for i := 0; i < 5*maxHandlers; i++ {
		st.writeHeaders(HeadersFrameParam{
			StreamID:      streamID,
			BlockFragment: st.encodeHeader(),
			EndStream:     true,
			EndHeaders:    true,
		})
		st.fr.WriteRSTStream(streamID, ErrCodeCancel)
		streamID += 2
	}
	fr := readFrame[*GoAwayFrame](t, st)
	if fr.ErrCode != ErrCodeEnhanceYourCalm {
		t.Errorf("err code = %v; want %v", fr.ErrCode, ErrCodeEnhanceYourCalm)
	}

	for _, s := range stops {
		close(s)
	}
}

func TestServerContinuationFlood(t *testing.T) { synctestTest(t, testServerContinuationFlood) }
func testServerContinuationFlood(t testing.TB) {
	st := newServerTester(t, func(w http.ResponseWriter, r *http.Request) {
		fmt.Println(r.Header)
	}, func(s *http.Server) {
		s.MaxHeaderBytes = 4096
	})
	defer st.Close()

	st.greet()

	st.writeHeaders(HeadersFrameParam{
		StreamID:      1,
		BlockFragment: st.encodeHeader(),
		EndStream:     true,
	})
	for i := 0; i < 1000; i++ {
		st.fr.WriteContinuation(1, false, st.encodeHeaderRaw(
			fmt.Sprintf("x-%v", i), "1234567890",
		))
	}
	st.fr.WriteContinuation(1, true, st.encodeHeaderRaw(
		"x-last-header", "1",
	))

	for {
		f := st.readFrame()
		if f == nil {
			break
		}
		switch f := f.(type) {
		case *HeadersFrame:
			t.Fatalf("received HEADERS frame; want GOAWAY and a closed connection")
		case *GoAwayFrame:
			// We might not see the GOAWAY (see below), but if we do it should
			// indicate that the server processed this request so the client doesn't
			// attempt to retry it.
			if got, want := f.LastStreamID, uint32(1); got != want {
				t.Errorf("received GOAWAY with LastStreamId %v, want %v", got, want)
			}

		}
	}
	// We expect to have seen a GOAWAY before the connection closes,
	// but the server will close the connection after one second
	// whether or not it has finished sending the GOAWAY. On windows-amd64-race
	// builders, this fairly consistently results in the connection closing without
	// the GOAWAY being sent.
	//
	// Since the server's behavior is inherently racy here and the important thing
	// is that the connection is closed, don't check for the GOAWAY having been sent.
}

func TestServerContinuationAfterInvalidHeader(t *testing.T) {
	synctestTest(t, testServerContinuationAfterInvalidHeader)
}
func testServerContinuationAfterInvalidHeader(t testing.TB) {
	st := newServerTester(t, func(w http.ResponseWriter, r *http.Request) {
		fmt.Println(r.Header)
	})
	defer st.Close()

	st.greet()

	st.writeHeaders(HeadersFrameParam{
		StreamID:      1,
		BlockFragment: st.encodeHeader(),
		EndStream:     true,
	})
	st.fr.WriteContinuation(1, false, st.encodeHeaderRaw(
		"x-invalid-header", "\x00",
	))
	st.fr.WriteContinuation(1, true, st.encodeHeaderRaw(
		"x-valid-header", "1",
	))

	var sawGoAway bool
	for {
		f := st.readFrame()
		if f == nil {
			break
		}
		switch f.(type) {
		case *GoAwayFrame:
			sawGoAway = true
		case *HeadersFrame:
			t.Fatalf("received HEADERS frame; want GOAWAY")
		}
	}
	if !sawGoAway {
		t.Errorf("connection closed with no GOAWAY frame; want one")
	}
}

func TestServerUpgradeRequestPrefaceFailure(t *testing.T) {
	synctestTest(t, testServerUpgradeRequestPrefaceFailure)
}
func testServerUpgradeRequestPrefaceFailure(t testing.TB) {
	// An h2c upgrade request fails when the client preface is not as expected.
	s2 := &Server{
		// Setting IdleTimeout triggers #67168.
		IdleTimeout: 60 * time.Minute,
	}
	c1, c2 := net.Pipe()
	donec := make(chan struct{})
	go func() {
		defer close(donec)
		s2.ServeConn(c1, &ServeConnOpts{
			UpgradeRequest: httptest.NewRequest("GET", "/", nil),
		})
	}()
	// The server expects to see the HTTP/2 preface,
	// but we close the connection instead.
	c2.Close()
	<-donec
}

// Issue 67036: A stream error should result in the handler's request context being canceled.
func TestServerRequestCancelOnError(t *testing.T) { synctestTest(t, testServerRequestCancelOnError) }
func testServerRequestCancelOnError(t testing.TB) {
	recvc := make(chan struct{}) // handler has started
	donec := make(chan struct{}) // handler has finished
	st := newServerTester(t, func(w http.ResponseWriter, r *http.Request) {
		close(recvc)
		<-r.Context().Done()
		close(donec)
	})
	defer st.Close()

	st.greet()

	// Client sends request headers, handler starts.
	st.writeHeaders(HeadersFrameParam{
		StreamID:      1,
		BlockFragment: st.encodeHeader(),
		EndStream:     true,
		EndHeaders:    true,
	})
	<-recvc

	// Client sends an invalid second set of request headers.
	// The stream is reset.
	// The handler's context is canceled, and the handler exits.
	st.writeHeaders(HeadersFrameParam{
		StreamID:      1,
		BlockFragment: st.encodeHeader(),
		EndStream:     true,
		EndHeaders:    true,
	})
	<-donec
}

func TestServerSetReadWriteDeadlineRace(t *testing.T) {
	synctestTest(t, testServerSetReadWriteDeadlineRace)
}
func testServerSetReadWriteDeadlineRace(t testing.TB) {
	ts := newTestServer(t, func(w http.ResponseWriter, r *http.Request) {
		ctl := http.NewResponseController(w)
		ctl.SetReadDeadline(time.Now().Add(3600 * time.Second))
		ctl.SetWriteDeadline(time.Now().Add(3600 * time.Second))
	})
	resp, err := ts.Client().Get(ts.URL)
	if err != nil {
		t.Fatal(err)
	}
	resp.Body.Close()
}

func TestServerWriteByteTimeout(t *testing.T) { synctestTest(t, testServerWriteByteTimeout) }
func testServerWriteByteTimeout(t testing.TB) {
	const timeout = 1 * time.Second
	st := newServerTester(t, func(w http.ResponseWriter, r *http.Request) {
		w.Write(make([]byte, 100))
	}, func(s *Server) {
		s.WriteByteTimeout = timeout
	})
	st.greet()

	st.cc.(*synctestNetConn).SetReadBufferSize(1) // write one byte at a time
	st.writeHeaders(HeadersFrameParam{
		StreamID:      1,
		BlockFragment: st.encodeHeader(),
		EndStream:     true,
		EndHeaders:    true,
	})

	// Read a few bytes, staying just under WriteByteTimeout.
	for i := 0; i < 10; i++ {
		st.advance(timeout - 1)
		if n, err := st.cc.Read(make([]byte, 1)); n != 1 || err != nil {
			t.Fatalf("read %v: %v, %v; want 1, nil", i, n, err)
		}
	}

	// Wait for WriteByteTimeout.
	// The connection should close.
	st.advance(1 * time.Second) // timeout after writing one byte
	st.advance(1 * time.Second) // timeout after failing to write any more bytes
	st.wantClosed()
}

func TestServerPingSent(t *testing.T) { synctestTest(t, testServerPingSent) }
func testServerPingSent(t testing.TB) {
	const readIdleTimeout = 15 * time.Second
	st := newServerTester(t, func(w http.ResponseWriter, r *http.Request) {
	}, func(s *Server) {
		s.ReadIdleTimeout = readIdleTimeout
	})
	st.greet()

	st.wantIdle()

	st.advance(readIdleTimeout)
	_ = readFrame[*PingFrame](t, st)
	st.wantIdle()

	st.advance(14 * time.Second)
	st.wantIdle()
	st.advance(1 * time.Second)
	st.wantClosed()
}

func TestServerPingResponded(t *testing.T) { synctestTest(t, testServerPingResponded) }
func testServerPingResponded(t testing.TB) {
	const readIdleTimeout = 15 * time.Second
	st := newServerTester(t, func(w http.ResponseWriter, r *http.Request) {
	}, func(s *Server) {
		s.ReadIdleTimeout = readIdleTimeout
	})
	st.greet()

	st.wantIdle()

	st.advance(readIdleTimeout)
	pf := readFrame[*PingFrame](t, st)
	st.wantIdle()

	st.advance(14 * time.Second)
	st.wantIdle()

	st.writePing(true, pf.Data)

	st.advance(2 * time.Second)
	st.wantIdle()
}

// golang.org/issue/15425: test that a handler closing the request
// body doesn't terminate the stream to the peer. (It just stops
// readability from the handler's side, and eventually the client
// runs out of flow control tokens)
func TestServerSendDataAfterRequestBodyClose(t *testing.T) {
	synctestTest(t, testServerSendDataAfterRequestBodyClose)
}
func testServerSendDataAfterRequestBodyClose(t testing.TB) {
	st := newServerTester(t, nil)
	st.greet()

	st.writeHeaders(HeadersFrameParam{
		StreamID:      1,
		BlockFragment: st.encodeHeader(),
		EndStream:     false,
		EndHeaders:    true,
	})

	// Handler starts writing the response body.
	call := st.nextHandlerCall()
	call.do(func(w http.ResponseWriter, req *http.Request) {
		w.Write([]byte("one"))
		http.NewResponseController(w).Flush()
	})
	st.wantFrameType(FrameHeaders)
	st.wantData(wantData{
		streamID:  1,
		endStream: false,
		data:      []byte("one"),
	})
	st.wantIdle()

	// Handler closes the request body.
	// This is not observable by the client.
	call.do(func(w http.ResponseWriter, req *http.Request) {
		req.Body.Close()
	})
	st.wantIdle()

	// The client can still send request data, which is discarded.
	st.writeData(1, false, []byte("client-sent data"))
	st.wantIdle()

	// Handler can still write more response body,
	// which is sent to the client.
	call.do(func(w http.ResponseWriter, req *http.Request) {
		w.Write([]byte("two"))
		http.NewResponseController(w).Flush()
	})
	st.wantData(wantData{
		streamID:  1,
		endStream: false,
		data:      []byte("two"),
	})
	st.wantIdle()
}

func TestServerSettingNoRFC7540Priorities(t *testing.T) {
	synctestTest(t, testServerSettingNoRFC7540Priorities)
}
func testServerSettingNoRFC7540Priorities(t testing.TB) {
	tests := []struct {
		ws                   func() WriteScheduler
		wantNoRFC7540Setting bool
	}{
		{
			ws: func() WriteScheduler {
				return NewPriorityWriteSchedulerRFC7540(nil)
			},
			wantNoRFC7540Setting: false,
		},
		{
			ws:                   NewPriorityWriteSchedulerRFC9218,
			wantNoRFC7540Setting: true,
		},
		{
			ws:                   NewRandomWriteScheduler,
			wantNoRFC7540Setting: true,
		},
		{
			ws:                   NewRoundRobinWriteScheduler,
			wantNoRFC7540Setting: true,
		},
	}
	for _, tt := range tests {
		st := newServerTester(t, nil, func(s *Server) {
			s.NewWriteScheduler = tt.ws
		})
		defer st.Close()

		var gotNoRFC7540Setting bool
		st.greetAndCheckSettings(func(s Setting) error {
			if s.ID != SettingNoRFC7540Priorities {
				return nil
			}
			gotNoRFC7540Setting = s.Val == 1
			return nil
		})
		if tt.wantNoRFC7540Setting != gotNoRFC7540Setting {
			t.Errorf("want SETTINGS_NO_RFC7540_PRIORITIES to be %v, got %v", tt.wantNoRFC7540Setting, gotNoRFC7540Setting)
		}
	}
}

func TestServerSettingNoRFC7540PrioritiesInvalid(t *testing.T) {
	synctestTest(t, testServerSettingNoRFC7540PrioritiesInvalid)
}
func testServerSettingNoRFC7540PrioritiesInvalid(t testing.TB) {
	st := newServerTester(t, nil)
	defer st.Close()

	st.writePreface()
	st.writeSettings(Setting{ID: SettingNoRFC7540Priorities, Val: 2})
	synctest.Wait()
	st.readFrame() // SETTINGS frame
	st.readFrame() // WINDOW_UPDATE frame
	st.wantGoAway(0, ErrCodeProtocol)
}

// This test documents current behavior, rather than ideal behavior that we
// would necessarily like to see. Refer to go.dev/issues/75936 for details.
func TestServerRFC7540PrioritySmallPayload(t *testing.T) {
	synctestTest(t, testServerRFC7540PrioritySmallPayload)
}
func testServerRFC7540PrioritySmallPayload(t testing.TB) {
	endTest := false
	st := newServerTester(t, func(w http.ResponseWriter, r *http.Request) {
		for !endTest {
			w.Write([]byte("a"))
			if f, ok := w.(http.Flusher); ok {
				f.Flush()
			}
		}
	}, func(s *Server) {
		s.NewWriteScheduler = func() WriteScheduler {
			return NewPriorityWriteSchedulerRFC7540(nil)
		}
	})
	if syncConn, ok := st.cc.(*synctestNetConn); ok {
		syncConn.SetReadBufferSize(1)
	} else {
		t.Fatal("Server connection is not synctestNetConn")
	}
	defer st.Close()
	defer func() { endTest = true }()
	st.greet()

	// Create 5 streams with weight of 0, and another 5 streams with weight of
	// 255.
	// Since each stream receives an infinite number of bytes, we should expect
	// to see that almost all of the response we get are for the streams with
	// weight of 255.
	for i := 1; i <= 19; i += 2 {
		weight := 1
		if i > 10 {
			weight = 255
		}
		st.writeHeaders(HeadersFrameParam{
			StreamID:      uint32(i),
			BlockFragment: st.encodeHeader(),
			EndStream:     true,
			EndHeaders:    true,
			Priority:      PriorityParam{StreamDep: 0, Weight: uint8(weight)},
		})
		synctest.Wait()
	}

	// In the current implementation however, the response we get are
	// distributed equally amongst all the streams, regardless of weight.
	streamWriteCount := make(map[uint32]int)
	totalWriteCount := 10000
	for range totalWriteCount {
		f := st.readFrame()
		if f == nil {
			break
		}
		streamWriteCount[f.Header().StreamID] += 1
	}
	for streamID, writeCount := range streamWriteCount {
		expectedWriteCount := totalWriteCount / len(streamWriteCount)
		errorMargin := expectedWriteCount / 100
		if writeCount >= expectedWriteCount+errorMargin || writeCount <= expectedWriteCount-errorMargin {
			t.Errorf("Expected stream %v to receive %v±%v writes, got %v", streamID, expectedWriteCount, errorMargin, writeCount)
		}
	}
}

// This test documents current behavior, rather than ideal behavior that we
// would necessarily like to see. Refer to go.dev/issues/75936 for details.
func TestServerRFC9218PrioritySmallPayload(t *testing.T) {
	synctestTest(t, testServerRFC9218PrioritySmallPayload)
}
func testServerRFC9218PrioritySmallPayload(t testing.TB) {
	endTest := false
	st := newServerTester(t, func(w http.ResponseWriter, r *http.Request) {
		for !endTest {
			w.Write([]byte("a"))
			if f, ok := w.(http.Flusher); ok {
				f.Flush()
			}
		}
	}, func(s *Server) {
		s.NewWriteScheduler = NewPriorityWriteSchedulerRFC9218
	})
	if syncConn, ok := st.cc.(*synctestNetConn); ok {
		syncConn.SetReadBufferSize(1)
	} else {
		t.Fatal("Server connection is not synctestNetConn")
	}
	defer st.Close()
	defer func() { endTest = true }()
	st.greet()

	// Create 5 streams with urgency of 0, and another 5 streams with urgency
	// of 7.
	// Since each stream receives an infinite number of bytes, we should expect
	// to see that almost all of the response we get are for the streams with
	// urgency of 0.
	for i := 1; i <= 19; i += 2 {
		urgency := uint8(0)
		if i > 10 {
			urgency = 7
		}
		st.writeHeaders(HeadersFrameParam{
			StreamID:      uint32(i),
			BlockFragment: st.encodeHeader("priority", fmt.Sprintf("u=%d", urgency)),
			EndStream:     true,
			EndHeaders:    true,
		})
		synctest.Wait()
	}

	// In the current implementation however, the response we get are
	// distributed equally amongst all the streams, regardless of weight.
	streamWriteCount := make(map[uint32]int)
	totalWriteCount := 10000
	for range totalWriteCount {
		f := st.readFrame()
		if f == nil {
			break
		}
		streamWriteCount[f.Header().StreamID] += 1
	}
	for streamID, writeCount := range streamWriteCount {
		expectedWriteCount := totalWriteCount / len(streamWriteCount)
		errorMargin := expectedWriteCount / 100
		if writeCount >= expectedWriteCount+errorMargin || writeCount <= expectedWriteCount-errorMargin {
			t.Errorf("Expected stream %v to receive %v±%v writes, got %v", streamID, expectedWriteCount, errorMargin, writeCount)
		}
	}
}

func TestServerRFC9218Priority(t *testing.T) {
	synctestTest(t, testServerRFC9218Priority)
}
func testServerRFC9218Priority(t testing.TB) {
	st := newServerTester(t, func(w http.ResponseWriter, r *http.Request) {
		w.Write(slices.Repeat([]byte("a"), 16<<20))
		if f, ok := w.(http.Flusher); ok {
			f.Flush()
		}
	}, func(s *Server) {
		s.NewWriteScheduler = NewPriorityWriteSchedulerRFC9218
	})
	defer st.Close()
	if syncConn, ok := st.cc.(*synctestNetConn); ok {
		syncConn.SetReadBufferSize(1)
	} else {
		t.Fatal("Server connection is not synctestNetConn")
	}
	st.greet()
	st.writeWindowUpdate(0, 1<<30)
	synctest.Wait()

	// Create 8 streams, where streams with larger ID has lower urgency value
	// (i.e. more urgent).
	for i := range 8 {
		streamID := uint32(i*2 + 1)
		urgency := 7 - i
		st.writeHeaders(HeadersFrameParam{
			StreamID:      streamID,
			BlockFragment: st.encodeHeader("priority", fmt.Sprintf("u=%d", urgency)),
			EndStream:     true,
			EndHeaders:    true,
		})
	}
	synctest.Wait()

	// Keep track of the last frame seen for each stream, indicating that they
	// are done being processed.
	lastFrame := make(map[uint32]int)
	for i := 0; ; i++ {
		f := st.readFrame()
		if f == nil {
			break
		}
		lastFrame[f.Header().StreamID] = i
	}
	for i := range 7 {
		streamID := uint32(i*2 + 1)
		nextStreamID := streamID + 2
		if lastFrame[streamID] < lastFrame[nextStreamID] {
			t.Errorf("stream %d finished before stream %d unexpectedly", streamID, nextStreamID)
		}
	}
}

func TestServerRFC9218PriorityIgnoredWhenProxied(t *testing.T) {
	synctestTest(t, testServerRFC9218PriorityIgnoredWhenProxied)
}
func testServerRFC9218PriorityIgnoredWhenProxied(t testing.TB) {
	st := newServerTester(t, func(w http.ResponseWriter, r *http.Request) {
		w.Write(slices.Repeat([]byte("a"), 16<<20))
		if f, ok := w.(http.Flusher); ok {
			f.Flush()
		}
	}, func(s *Server) {
		s.NewWriteScheduler = NewPriorityWriteSchedulerRFC9218
	})
	defer st.Close()
	if syncConn, ok := st.cc.(*synctestNetConn); ok {
		syncConn.SetReadBufferSize(1)
	} else {
		t.Fatal("Server connection is not synctestNetConn")
	}
	st.greet()
	st.writeWindowUpdate(0, 1<<30)
	synctest.Wait()

	// Create 8 streams, where streams with larger ID has lower urgency value
	// (i.e. more urgent). These should be ignored since the requests are
	// coming through a proxy.
	for i := range 8 {
		streamID := uint32(i*2 + 1)
		urgency := 7 - i
		st.writeHeaders(HeadersFrameParam{
			StreamID:      streamID,
			BlockFragment: st.encodeHeader("priority", fmt.Sprintf("u=%d", urgency), "via", "a proxy"),
			EndStream:     true,
			EndHeaders:    true,
		})
	}
	synctest.Wait()
	var streamFrameOrder []uint32
	for f := st.readFrame(); f != nil; f = st.readFrame() {
		streamFrameOrder = append(streamFrameOrder, f.Header().StreamID)
	}
	// Only check the middle-half of the frame processing order, since the
	// beginning and end can be not perfectly round-robin (e.g. stream 1 gets
	// processed a few times while waiting before other streams are opened).
	half := streamFrameOrder[len(streamFrameOrder)/4 : len(streamFrameOrder)*3/4]
	if !slices.Equal(slices.Compact(half), half) {
		t.Errorf("want stream to be processed in round-robin manner when proxied, got: %v", streamFrameOrder)
	}
}

func TestServerRFC9218PriorityAware(t *testing.T) {
	synctestTest(t, testServerRFC9218PriorityAware)
}
func testServerRFC9218PriorityAware(t testing.TB) {
	st := newServerTester(t, func(w http.ResponseWriter, r *http.Request) {
		w.Write(slices.Repeat([]byte("a"), 16<<20))
		if f, ok := w.(http.Flusher); ok {
			f.Flush()
		}
	}, func(s *Server) {
		s.NewWriteScheduler = NewPriorityWriteSchedulerRFC9218
	})
	defer st.Close()
	if syncConn, ok := st.cc.(*synctestNetConn); ok {
		syncConn.SetReadBufferSize(1)
	} else {
		t.Fatal("Server connection is not synctestNetConn")
	}
	st.greet()
	st.writeWindowUpdate(0, 1<<30)
	synctest.Wait()

	// When there is no indication that the client is aware of RFC 9218
	// priority, it should process streams in a round-robin manner.
	streamCount := 10
	for i := range streamCount {
		streamID := uint32(i*2 + 1)
		st.writeHeaders(HeadersFrameParam{
			StreamID:      streamID,
			BlockFragment: st.encodeHeader(),
			EndStream:     true,
			EndHeaders:    true,
		})
	}
	synctest.Wait()
	var streamFrameOrder []uint32
	for f := st.readFrame(); f != nil; f = st.readFrame() {
		streamFrameOrder = append(streamFrameOrder, f.Header().StreamID)
	}
	// Only check the middle-half of the frame processing order, since the
	// beginning and end can be not perfectly round-robin (e.g. stream 1 gets
	// processed a few times while waiting before other streams are opened).
	half := streamFrameOrder[len(streamFrameOrder)/4 : len(streamFrameOrder)*3/4]
	if !slices.Equal(slices.Compact(half), half) {
		t.Errorf("want stream to be processed in round-robin manner when unaware of priority, got: %v", streamFrameOrder)
	}

	// Send a PRIORITY_UPDATE frame for stream 1 which would have finished by
	// now. So, this is a no-op, but makes it so that the server is aware that
	// the client is aware of RFC 9218 priority.
	st.writePriorityUpdate(1, "")
	synctest.Wait()

	// Now that the server knows that the client is aware of RFC 9218 priority,
	// streams should be processed one-by-one to completion when no explicit
	// priority is given as they all have the same urgency and are
	// non-incremental.
	streamFrameOrder = []uint32{}
	for i := range streamCount {
		i += streamCount
		streamID := uint32(i*2 + 1)
		st.writeHeaders(HeadersFrameParam{
			StreamID:      streamID,
			BlockFragment: st.encodeHeader(),
			EndStream:     true,
			EndHeaders:    true,
		})
	}
	for f := st.readFrame(); f != nil; f = st.readFrame() {
		streamFrameOrder = append(streamFrameOrder, f.Header().StreamID)
	}
	if !slices.Equal(slices.Compact(half), half) {
		t.Errorf("want stream to be processed one-by-one to completion when aware of priority, got: %v", streamFrameOrder)
	}
}
