github.com/binkynet/BinkyNet@v1.12.1-0.20240421190447-da4e34c20be0/proto_vendor/golang.org/x/net/http2/http2.go (about)

     1  // Copyright 2014 The Go Authors. All rights reserved.
     2  // Use of this source code is governed by a BSD-style
     3  // license that can be found in the LICENSE file.
     4  
     5  // Package http2 implements the HTTP/2 protocol.
     6  //
     7  // This package is low-level and intended to be used directly by very
     8  // few people. Most users will use it indirectly through the automatic
     9  // use by the net/http package (from Go 1.6 and later).
    10  // For use in earlier Go versions see ConfigureServer. (Transport support
    11  // requires Go 1.6 or later)
    12  //
    13  // See https://http2.github.io/ for more information on HTTP/2.
    14  //
    15  // See https://http2.golang.org/ for a test server running this code.
    16  //
    17  package http2 // import "golang.org/x/net/http2"
    18  
    19  import (
    20  	"bufio"
    21  	"crypto/tls"
    22  	"errors"
    23  	"fmt"
    24  	"io"
    25  	"net/http"
    26  	"os"
    27  	"sort"
    28  	"strconv"
    29  	"strings"
    30  	"sync"
    31  
    32  	"golang.org/x/net/http/httpguts"
    33  )
    34  
    35  var (
    36  	VerboseLogs    bool
    37  	logFrameWrites bool
    38  	logFrameReads  bool
    39  	inTests        bool
    40  )
    41  
    42  func init() {
    43  	e := os.Getenv("GODEBUG")
    44  	if strings.Contains(e, "http2debug=1") {
    45  		VerboseLogs = true
    46  	}
    47  	if strings.Contains(e, "http2debug=2") {
    48  		VerboseLogs = true
    49  		logFrameWrites = true
    50  		logFrameReads = true
    51  	}
    52  }
    53  
    54  const (
    55  	// ClientPreface is the string that must be sent by new
    56  	// connections from clients.
    57  	ClientPreface = "PRI * HTTP/2.0\r\n\r\nSM\r\n\r\n"
    58  
    59  	// SETTINGS_MAX_FRAME_SIZE default
    60  	// http://http2.github.io/http2-spec/#rfc.section.6.5.2
    61  	initialMaxFrameSize = 16384
    62  
    63  	// NextProtoTLS is the NPN/ALPN protocol negotiated during
    64  	// HTTP/2's TLS setup.
    65  	NextProtoTLS = "h2"
    66  
    67  	// http://http2.github.io/http2-spec/#SettingValues
    68  	initialHeaderTableSize = 4096
    69  
    70  	initialWindowSize = 65535 // 6.9.2 Initial Flow Control Window Size
    71  
    72  	defaultMaxReadFrameSize = 1 << 20
    73  )
    74  
    75  var (
    76  	clientPreface = []byte(ClientPreface)
    77  )
    78  
    79  type streamState int
    80  
    81  // HTTP/2 stream states.
    82  //
    83  // See http://tools.ietf.org/html/rfc7540#section-5.1.
    84  //
    85  // For simplicity, the server code merges "reserved (local)" into
    86  // "half-closed (remote)". This is one less state transition to track.
    87  // The only downside is that we send PUSH_PROMISEs slightly less
    88  // liberally than allowable. More discussion here:
    89  // https://lists.w3.org/Archives/Public/ietf-http-wg/2016JulSep/0599.html
    90  //
    91  // "reserved (remote)" is omitted since the client code does not
    92  // support server push.
    93  const (
    94  	stateIdle streamState = iota
    95  	stateOpen
    96  	stateHalfClosedLocal
    97  	stateHalfClosedRemote
    98  	stateClosed
    99  )
   100  
   101  var stateName = [...]string{
   102  	stateIdle:             "Idle",
   103  	stateOpen:             "Open",
   104  	stateHalfClosedLocal:  "HalfClosedLocal",
   105  	stateHalfClosedRemote: "HalfClosedRemote",
   106  	stateClosed:           "Closed",
   107  }
   108  
   109  func (st streamState) String() string {
   110  	return stateName[st]
   111  }
   112  
   113  // Setting is a setting parameter: which setting it is, and its value.
   114  type Setting struct {
   115  	// ID is which setting is being set.
   116  	// See http://http2.github.io/http2-spec/#SettingValues
   117  	ID SettingID
   118  
   119  	// Val is the value.
   120  	Val uint32
   121  }
   122  
   123  func (s Setting) String() string {
   124  	return fmt.Sprintf("[%v = %d]", s.ID, s.Val)
   125  }
   126  
   127  // Valid reports whether the setting is valid.
   128  func (s Setting) Valid() error {
   129  	// Limits and error codes from 6.5.2 Defined SETTINGS Parameters
   130  	switch s.ID {
   131  	case SettingEnablePush:
   132  		if s.Val != 1 && s.Val != 0 {
   133  			return ConnectionError(ErrCodeProtocol)
   134  		}
   135  	case SettingInitialWindowSize:
   136  		if s.Val > 1<<31-1 {
   137  			return ConnectionError(ErrCodeFlowControl)
   138  		}
   139  	case SettingMaxFrameSize:
   140  		if s.Val < 16384 || s.Val > 1<<24-1 {
   141  			return ConnectionError(ErrCodeProtocol)
   142  		}
   143  	}
   144  	return nil
   145  }
   146  
   147  // A SettingID is an HTTP/2 setting as defined in
   148  // http://http2.github.io/http2-spec/#iana-settings
   149  type SettingID uint16
   150  
   151  const (
   152  	SettingHeaderTableSize      SettingID = 0x1
   153  	SettingEnablePush           SettingID = 0x2
   154  	SettingMaxConcurrentStreams SettingID = 0x3
   155  	SettingInitialWindowSize    SettingID = 0x4
   156  	SettingMaxFrameSize         SettingID = 0x5
   157  	SettingMaxHeaderListSize    SettingID = 0x6
   158  )
   159  
   160  var settingName = map[SettingID]string{
   161  	SettingHeaderTableSize:      "HEADER_TABLE_SIZE",
   162  	SettingEnablePush:           "ENABLE_PUSH",
   163  	SettingMaxConcurrentStreams: "MAX_CONCURRENT_STREAMS",
   164  	SettingInitialWindowSize:    "INITIAL_WINDOW_SIZE",
   165  	SettingMaxFrameSize:         "MAX_FRAME_SIZE",
   166  	SettingMaxHeaderListSize:    "MAX_HEADER_LIST_SIZE",
   167  }
   168  
   169  func (s SettingID) String() string {
   170  	if v, ok := settingName[s]; ok {
   171  		return v
   172  	}
   173  	return fmt.Sprintf("UNKNOWN_SETTING_%d", uint16(s))
   174  }
   175  
   176  var (
   177  	errInvalidHeaderFieldName  = errors.New("http2: invalid header field name")
   178  	errInvalidHeaderFieldValue = errors.New("http2: invalid header field value")
   179  )
   180  
   181  // validWireHeaderFieldName reports whether v is a valid header field
   182  // name (key). See httpguts.ValidHeaderName for the base rules.
   183  //
   184  // Further, http2 says:
   185  //   "Just as in HTTP/1.x, header field names are strings of ASCII
   186  //   characters that are compared in a case-insensitive
   187  //   fashion. However, header field names MUST be converted to
   188  //   lowercase prior to their encoding in HTTP/2. "
   189  func validWireHeaderFieldName(v string) bool {
   190  	if len(v) == 0 {
   191  		return false
   192  	}
   193  	for _, r := range v {
   194  		if !httpguts.IsTokenRune(r) {
   195  			return false
   196  		}
   197  		if 'A' <= r && r <= 'Z' {
   198  			return false
   199  		}
   200  	}
   201  	return true
   202  }
   203  
   204  func httpCodeString(code int) string {
   205  	switch code {
   206  	case 200:
   207  		return "200"
   208  	case 404:
   209  		return "404"
   210  	}
   211  	return strconv.Itoa(code)
   212  }
   213  
   214  // from pkg io
   215  type stringWriter interface {
   216  	WriteString(s string) (n int, err error)
   217  }
   218  
   219  // A gate lets two goroutines coordinate their activities.
   220  type gate chan struct{}
   221  
   222  func (g gate) Done() { g <- struct{}{} }
   223  func (g gate) Wait() { <-g }
   224  
   225  // A closeWaiter is like a sync.WaitGroup but only goes 1 to 0 (open to closed).
   226  type closeWaiter chan struct{}
   227  
   228  // Init makes a closeWaiter usable.
   229  // It exists because so a closeWaiter value can be placed inside a
   230  // larger struct and have the Mutex and Cond's memory in the same
   231  // allocation.
   232  func (cw *closeWaiter) Init() {
   233  	*cw = make(chan struct{})
   234  }
   235  
   236  // Close marks the closeWaiter as closed and unblocks any waiters.
   237  func (cw closeWaiter) Close() {
   238  	close(cw)
   239  }
   240  
   241  // Wait waits for the closeWaiter to become closed.
   242  func (cw closeWaiter) Wait() {
   243  	<-cw
   244  }
   245  
   246  // bufferedWriter is a buffered writer that writes to w.
   247  // Its buffered writer is lazily allocated as needed, to minimize
   248  // idle memory usage with many connections.
   249  type bufferedWriter struct {
   250  	w  io.Writer     // immutable
   251  	bw *bufio.Writer // non-nil when data is buffered
   252  }
   253  
   254  func newBufferedWriter(w io.Writer) *bufferedWriter {
   255  	return &bufferedWriter{w: w}
   256  }
   257  
   258  // bufWriterPoolBufferSize is the size of bufio.Writer's
   259  // buffers created using bufWriterPool.
   260  //
   261  // TODO: pick a less arbitrary value? this is a bit under
   262  // (3 x typical 1500 byte MTU) at least. Other than that,
   263  // not much thought went into it.
   264  const bufWriterPoolBufferSize = 4 << 10
   265  
   266  var bufWriterPool = sync.Pool{
   267  	New: func() interface{} {
   268  		return bufio.NewWriterSize(nil, bufWriterPoolBufferSize)
   269  	},
   270  }
   271  
   272  func (w *bufferedWriter) Available() int {
   273  	if w.bw == nil {
   274  		return bufWriterPoolBufferSize
   275  	}
   276  	return w.bw.Available()
   277  }
   278  
   279  func (w *bufferedWriter) Write(p []byte) (n int, err error) {
   280  	if w.bw == nil {
   281  		bw := bufWriterPool.Get().(*bufio.Writer)
   282  		bw.Reset(w.w)
   283  		w.bw = bw
   284  	}
   285  	return w.bw.Write(p)
   286  }
   287  
   288  func (w *bufferedWriter) Flush() error {
   289  	bw := w.bw
   290  	if bw == nil {
   291  		return nil
   292  	}
   293  	err := bw.Flush()
   294  	bw.Reset(nil)
   295  	bufWriterPool.Put(bw)
   296  	w.bw = nil
   297  	return err
   298  }
   299  
   300  func mustUint31(v int32) uint32 {
   301  	if v < 0 || v > 2147483647 {
   302  		panic("out of range")
   303  	}
   304  	return uint32(v)
   305  }
   306  
   307  // bodyAllowedForStatus reports whether a given response status code
   308  // permits a body. See RFC 7230, section 3.3.
   309  func bodyAllowedForStatus(status int) bool {
   310  	switch {
   311  	case status >= 100 && status <= 199:
   312  		return false
   313  	case status == 204:
   314  		return false
   315  	case status == 304:
   316  		return false
   317  	}
   318  	return true
   319  }
   320  
   321  type httpError struct {
   322  	msg     string
   323  	timeout bool
   324  }
   325  
   326  func (e *httpError) Error() string   { return e.msg }
   327  func (e *httpError) Timeout() bool   { return e.timeout }
   328  func (e *httpError) Temporary() bool { return true }
   329  
   330  var errTimeout error = &httpError{msg: "http2: timeout awaiting response headers", timeout: true}
   331  
   332  type connectionStater interface {
   333  	ConnectionState() tls.ConnectionState
   334  }
   335  
   336  var sorterPool = sync.Pool{New: func() interface{} { return new(sorter) }}
   337  
   338  type sorter struct {
   339  	v []string // owned by sorter
   340  }
   341  
   342  func (s *sorter) Len() int           { return len(s.v) }
   343  func (s *sorter) Swap(i, j int)      { s.v[i], s.v[j] = s.v[j], s.v[i] }
   344  func (s *sorter) Less(i, j int) bool { return s.v[i] < s.v[j] }
   345  
   346  // Keys returns the sorted keys of h.
   347  //
   348  // The returned slice is only valid until s used again or returned to
   349  // its pool.
   350  func (s *sorter) Keys(h http.Header) []string {
   351  	keys := s.v[:0]
   352  	for k := range h {
   353  		keys = append(keys, k)
   354  	}
   355  	s.v = keys
   356  	sort.Sort(s)
   357  	return keys
   358  }
   359  
   360  func (s *sorter) SortStrings(ss []string) {
   361  	// Our sorter works on s.v, which sorter owns, so
   362  	// stash it away while we sort the user's buffer.
   363  	save := s.v
   364  	s.v = ss
   365  	sort.Sort(s)
   366  	s.v = save
   367  }
   368  
   369  // validPseudoPath reports whether v is a valid :path pseudo-header
   370  // value. It must be either:
   371  //
   372  //     *) a non-empty string starting with '/'
   373  //     *) the string '*', for OPTIONS requests.
   374  //
   375  // For now this is only used a quick check for deciding when to clean
   376  // up Opaque URLs before sending requests from the Transport.
   377  // See golang.org/issue/16847
   378  //
   379  // We used to enforce that the path also didn't start with "//", but
   380  // Google's GFE accepts such paths and Chrome sends them, so ignore
   381  // that part of the spec. See golang.org/issue/19103.
   382  func validPseudoPath(v string) bool {
   383  	return (len(v) > 0 && v[0] == '/') || v == "*"
   384  }