package fasthttp

import (
	
	
	
	
	
	
	
	
	
	
	
	
	
	
)

var errNoCertOrKeyProvided = errors.New("cert or key has not provided")

// Deprecated: ErrAlreadyServing is never returned from Serve. See issue #633.
var ErrAlreadyServing = errors.New("Server is already serving connections")

// ServeConn serves HTTP requests from the given connection
// using the given handler.
//
// ServeConn returns nil if all requests from the c are successfully served.
// It returns non-nil error otherwise.
//
// Connection c must immediately propagate all the data passed to Write()
// to the client. Otherwise requests' processing may hang.
//
// ServeConn closes c before returning.
func ( net.Conn,  RequestHandler) error {
	 := serverPool.Get()
	if  == nil {
		 = &Server{}
	}
	 := .(*Server)
	.Handler = 
	 := .ServeConn()
	.Handler = nil
	serverPool.Put()
	return 
}

var serverPool sync.Pool

// Serve serves incoming connections from the given listener
// using the given handler.
//
// Serve blocks until the given listener returns permanent error.
func ( net.Listener,  RequestHandler) error {
	 := &Server{
		Handler: ,
	}
	return .Serve()
}

// ServeTLS serves HTTPS requests from the given net.Listener
// using the given handler.
//
// certFile and keyFile are paths to TLS certificate and key files.
func ( net.Listener, ,  string,  RequestHandler) error {
	 := &Server{
		Handler: ,
	}
	return .ServeTLS(, , )
}

// ServeTLSEmbed serves HTTPS requests from the given net.Listener
// using the given handler.
//
// certData and keyData must contain valid TLS certificate and key data.
func ( net.Listener, ,  []byte,  RequestHandler) error {
	 := &Server{
		Handler: ,
	}
	return .ServeTLSEmbed(, , )
}

// ListenAndServe serves HTTP requests from the given TCP addr
// using the given handler.
func ( string,  RequestHandler) error {
	 := &Server{
		Handler: ,
	}
	return .ListenAndServe()
}

// ListenAndServeUNIX serves HTTP requests from the given UNIX addr
// using the given handler.
//
// The function deletes existing file at addr before starting serving.
//
// The server sets the given file mode for the UNIX addr.
func ( string,  os.FileMode,  RequestHandler) error {
	 := &Server{
		Handler: ,
	}
	return .ListenAndServeUNIX(, )
}

// ListenAndServeTLS serves HTTPS requests from the given TCP addr
// using the given handler.
//
// certFile and keyFile are paths to TLS certificate and key files.
func (, ,  string,  RequestHandler) error {
	 := &Server{
		Handler: ,
	}
	return .ListenAndServeTLS(, , )
}

// ListenAndServeTLSEmbed serves HTTPS requests from the given TCP addr
// using the given handler.
//
// certData and keyData must contain valid TLS certificate and key data.
func ( string, ,  []byte,  RequestHandler) error {
	 := &Server{
		Handler: ,
	}
	return .ListenAndServeTLSEmbed(, , )
}

// RequestHandler must process incoming requests.
//
// RequestHandler must call ctx.TimeoutError() before returning
// if it keeps references to ctx and/or its members after the return.
// Consider wrapping RequestHandler into TimeoutHandler if response time
// must be limited.
type RequestHandler func(ctx *RequestCtx)

// ServeHandler must process tls.Config.NextProto negotiated requests.
type ServeHandler func(c net.Conn) error

// Server implements HTTP server.
//
// Default Server settings should satisfy the majority of Server users.
// Adjust Server settings only if you really understand the consequences.
//
// It is forbidden copying Server instances. Create new Server instances
// instead.
//
// It is safe to call Server methods from concurrently running goroutines.
type Server struct {
	noCopy noCopy

	// Handler for processing incoming requests.
	//
	// Take into account that no `panic` recovery is done by `fasthttp` (thus any `panic` will take down the entire server).
	// Instead the user should use `recover` to handle these situations.
	Handler RequestHandler

	// ErrorHandler for returning a response in case of an error while receiving or parsing the request.
	//
	// The following is a non-exhaustive list of errors that can be expected as argument:
	//   * io.EOF
	//   * io.ErrUnexpectedEOF
	//   * ErrGetOnly
	//   * ErrSmallBuffer
	//   * ErrBodyTooLarge
	//   * ErrBrokenChunks
	ErrorHandler func(ctx *RequestCtx, err error)

	// HeaderReceived is called after receiving the header
	//
	// non zero RequestConfig field values will overwrite the default configs
	HeaderReceived func(header *RequestHeader) RequestConfig

	// ContinueHandler is called after receiving the Expect 100 Continue Header
	//
	// https://www.w3.org/Protocols/rfc2616/rfc2616-sec8.html#sec8.2.3
	// https://www.w3.org/Protocols/rfc2616/rfc2616-sec10.html#sec10.1.1
	// Using ContinueHandler a server can make decisioning on whether or not
	// to read a potentially large request body based on the headers
	//
	// The default is to automatically read request bodies of Expect 100 Continue requests
	// like they are normal requests
	ContinueHandler func(header *RequestHeader) bool

	// Server name for sending in response headers.
	//
	// Default server name is used if left blank.
	Name string

	// The maximum number of concurrent connections the server may serve.
	//
	// DefaultConcurrency is used if not set.
	//
	// Concurrency only works if you either call Serve once, or only ServeConn multiple times.
	// It works with ListenAndServe as well.
	Concurrency int

	// Per-connection buffer size for requests' reading.
	// This also limits the maximum header size.
	//
	// Increase this buffer if your clients send multi-KB RequestURIs
	// and/or multi-KB headers (for example, BIG cookies).
	//
	// Default buffer size is used if not set.
	ReadBufferSize int

	// Per-connection buffer size for responses' writing.
	//
	// Default buffer size is used if not set.
	WriteBufferSize int

	// ReadTimeout is the amount of time allowed to read
	// the full request including body. The connection's read
	// deadline is reset when the connection opens, or for
	// keep-alive connections after the first byte has been read.
	//
	// By default request read timeout is unlimited.
	ReadTimeout time.Duration

	// WriteTimeout is the maximum duration before timing out
	// writes of the response. It is reset after the request handler
	// has returned.
	//
	// By default response write timeout is unlimited.
	WriteTimeout time.Duration

	// IdleTimeout is the maximum amount of time to wait for the
	// next request when keep-alive is enabled. If IdleTimeout
	// is zero, the value of ReadTimeout is used.
	IdleTimeout time.Duration

	// Maximum number of concurrent client connections allowed per IP.
	//
	// By default unlimited number of concurrent connections
	// may be established to the server from a single IP address.
	MaxConnsPerIP int

	// Maximum number of requests served per connection.
	//
	// The server closes connection after the last request.
	// 'Connection: close' header is added to the last response.
	//
	// By default unlimited number of requests may be served per connection.
	MaxRequestsPerConn int

	// MaxKeepaliveDuration is a no-op and only left here for backwards compatibility.
	// Deprecated: Use IdleTimeout instead.
	MaxKeepaliveDuration time.Duration

	// MaxIdleWorkerDuration is the maximum idle time of a single worker in the underlying
	// worker pool of the Server. Idle workers beyond this time will be cleared.
	MaxIdleWorkerDuration time.Duration

	// Period between tcp keep-alive messages.
	//
	// TCP keep-alive period is determined by operation system by default.
	TCPKeepalivePeriod time.Duration

	// Maximum request body size.
	//
	// The server rejects requests with bodies exceeding this limit.
	//
	// Request body size is limited by DefaultMaxRequestBodySize by default.
	MaxRequestBodySize int

	// Whether to disable keep-alive connections.
	//
	// The server will close all the incoming connections after sending
	// the first response to client if this option is set to true.
	//
	// By default keep-alive connections are enabled.
	DisableKeepalive bool

	// Whether to enable tcp keep-alive connections.
	//
	// Whether the operating system should send tcp keep-alive messages on the tcp connection.
	//
	// By default tcp keep-alive connections are disabled.
	TCPKeepalive bool

	// Aggressively reduces memory usage at the cost of higher CPU usage
	// if set to true.
	//
	// Try enabling this option only if the server consumes too much memory
	// serving mostly idle keep-alive connections. This may reduce memory
	// usage by more than 50%.
	//
	// Aggressive memory usage reduction is disabled by default.
	ReduceMemoryUsage bool

	// Rejects all non-GET requests if set to true.
	//
	// This option is useful as anti-DoS protection for servers
	// accepting only GET requests and HEAD requests. The request size is limited
	// by ReadBufferSize if GetOnly is set.
	//
	// Server accepts all the requests by default.
	GetOnly bool

	// Will not pre parse Multipart Form data if set to true.
	//
	// This option is useful for servers that desire to treat
	// multipart form data as a binary blob, or choose when to parse the data.
	//
	// Server pre parses multipart form data by default.
	DisablePreParseMultipartForm bool

	// Logs all errors, including the most frequent
	// 'connection reset by peer', 'broken pipe' and 'connection timeout'
	// errors. Such errors are common in production serving real-world
	// clients.
	//
	// By default the most frequent errors such as
	// 'connection reset by peer', 'broken pipe' and 'connection timeout'
	// are suppressed in order to limit output log traffic.
	LogAllErrors bool

	// Will not log potentially sensitive content in error logs
	//
	// This option is useful for servers that handle sensitive data
	// in the request/response.
	//
	// Server logs all full errors by default.
	SecureErrorLogMessage bool

	// Header names are passed as-is without normalization
	// if this option is set.
	//
	// Disabled header names' normalization may be useful only for proxying
	// incoming requests to other servers expecting case-sensitive
	// header names. See https://github.com/valyala/fasthttp/issues/57
	// for details.
	//
	// By default request and response header names are normalized, i.e.
	// The first letter and the first letters following dashes
	// are uppercased, while all the other letters are lowercased.
	// Examples:
	//
	//     * HOST -> Host
	//     * content-type -> Content-Type
	//     * cONTENT-lenGTH -> Content-Length
	DisableHeaderNamesNormalizing bool

	// SleepWhenConcurrencyLimitsExceeded is a duration to be slept of if
	// the concurrency limit in exceeded (default [when is 0]: don't sleep
	// and accept new connections immediately).
	SleepWhenConcurrencyLimitsExceeded time.Duration

	// NoDefaultServerHeader, when set to true, causes the default Server header
	// to be excluded from the Response.
	//
	// The default Server header value is the value of the Name field or an
	// internal default value in its absence. With this option set to true,
	// the only time a Server header will be sent is if a non-zero length
	// value is explicitly provided during a request.
	NoDefaultServerHeader bool

	// NoDefaultDate, when set to true, causes the default Date
	// header to be excluded from the Response.
	//
	// The default Date header value is the current date value. When
	// set to true, the Date will not be present.
	NoDefaultDate bool

	// NoDefaultContentType, when set to true, causes the default Content-Type
	// header to be excluded from the Response.
	//
	// The default Content-Type header value is the internal default value. When
	// set to true, the Content-Type will not be present.
	NoDefaultContentType bool

	// KeepHijackedConns is an opt-in disable of connection
	// close by fasthttp after connections' HijackHandler returns.
	// This allows to save goroutines, e.g. when fasthttp used to upgrade
	// http connections to WS and connection goes to another handler,
	// which will close it when needed.
	KeepHijackedConns bool

	// CloseOnShutdown when true adds a `Connection: close` header when the server is shutting down.
	CloseOnShutdown bool

	// StreamRequestBody enables request body streaming,
	// and calls the handler sooner when given body is
	// larger than the current limit.
	StreamRequestBody bool

	// ConnState specifies an optional callback function that is
	// called when a client connection changes state. See the
	// ConnState type and associated constants for details.
	ConnState func(net.Conn, ConnState)

	// Logger, which is used by RequestCtx.Logger().
	//
	// By default standard logger from log package is used.
	Logger Logger

	// TLSConfig optionally provides a TLS configuration for use
	// by ServeTLS, ServeTLSEmbed, ListenAndServeTLS, ListenAndServeTLSEmbed,
	// AppendCert, AppendCertEmbed and NextProto.
	//
	// Note that this value is cloned by ServeTLS, ServeTLSEmbed, ListenAndServeTLS
	// and ListenAndServeTLSEmbed, so it's not possible to modify the configuration
	// with methods like tls.Config.SetSessionTicketKeys.
	// To use SetSessionTicketKeys, use Server.Serve with a TLS Listener
	// instead.
	TLSConfig *tls.Config

	// FormValueFunc, which is used by RequestCtx.FormValue and support for customizing
	// the behaviour of the RequestCtx.FormValue function.
	//
	// NetHttpFormValueFunc gives a FormValueFunc func implementation that is consistent with net/http.
	FormValueFunc FormValueFunc

	nextProtos map[string]ServeHandler

	concurrency      uint32
	concurrencyCh    chan struct{}
	perIPConnCounter perIPConnCounter

	ctxPool        sync.Pool
	readerPool     sync.Pool
	writerPool     sync.Pool
	hijackConnPool sync.Pool

	// We need to know our listeners and idle connections so we can close them in Shutdown().
	ln []net.Listener

	idleConns   map[net.Conn]time.Time
	idleConnsMu sync.Mutex

	mu   sync.Mutex
	open int32
	stop int32
	done chan struct{}
}

// TimeoutHandler creates RequestHandler, which returns StatusRequestTimeout
// error with the given msg to the client if h didn't return during
// the given duration.
//
// The returned handler may return StatusTooManyRequests error with the given
// msg to the client if there are more than Server.Concurrency concurrent
// handlers h are running at the moment.
func ( RequestHandler,  time.Duration,  string) RequestHandler {
	return TimeoutWithCodeHandler(, , , StatusRequestTimeout)
}

// TimeoutWithCodeHandler creates RequestHandler, which returns an error with
// the given msg and status code to the client  if h didn't return during
// the given duration.
//
// The returned handler may return StatusTooManyRequests error with the given
// msg to the client if there are more than Server.Concurrency concurrent
// handlers h are running at the moment.
func ( RequestHandler,  time.Duration,  string,  int) RequestHandler {
	if  <= 0 {
		return 
	}

	return func( *RequestCtx) {
		 := .s.concurrencyCh
		select {
		case  <- struct{}{}:
		default:
			.Error(, StatusTooManyRequests)
			return
		}

		 := .timeoutCh
		if  == nil {
			 = make(chan struct{}, 1)
			.timeoutCh = 
		}
		go func() {
			()
			 <- struct{}{}
			<-
		}()
		.timeoutTimer = initTimer(.timeoutTimer, )
		select {
		case <-:
		case <-.timeoutTimer.C:
			.TimeoutErrorWithCode(, )
		}
		stopTimer(.timeoutTimer)
	}
}

// RequestConfig configure the per request deadline and body limits
type RequestConfig struct {
	// ReadTimeout is the maximum duration for reading the entire
	// request body.
	// a zero value means that default values will be honored
	ReadTimeout time.Duration
	// WriteTimeout is the maximum duration before timing out
	// writes of the response.
	// a zero value means that default values will be honored
	WriteTimeout time.Duration
	// Maximum request body size.
	// a zero value means that default values will be honored
	MaxRequestBodySize int
}

// CompressHandler returns RequestHandler that transparently compresses
// response body generated by h if the request contains 'gzip' or 'deflate'
// 'Accept-Encoding' header.
func ( RequestHandler) RequestHandler {
	return CompressHandlerLevel(, CompressDefaultCompression)
}

// CompressHandlerLevel returns RequestHandler that transparently compresses
// response body generated by h if the request contains a 'gzip' or 'deflate'
// 'Accept-Encoding' header.
//
// Level is the desired compression level:
//
//   - CompressNoCompression
//   - CompressBestSpeed
//   - CompressBestCompression
//   - CompressDefaultCompression
//   - CompressHuffmanOnly
func ( RequestHandler,  int) RequestHandler {
	return func( *RequestCtx) {
		()
		if .Request.Header.HasAcceptEncodingBytes(strGzip) {
			.Response.gzipBody() //nolint:errcheck
		} else if .Request.Header.HasAcceptEncodingBytes(strDeflate) {
			.Response.deflateBody() //nolint:errcheck
		}
	}
}

// CompressHandlerBrotliLevel returns RequestHandler that transparently compresses
// response body generated by h if the request contains a 'br', 'gzip' or 'deflate'
// 'Accept-Encoding' header.
//
// brotliLevel is the desired compression level for brotli.
//
//   - CompressBrotliNoCompression
//   - CompressBrotliBestSpeed
//   - CompressBrotliBestCompression
//   - CompressBrotliDefaultCompression
//
// otherLevel is the desired compression level for gzip and deflate.
//
//   - CompressNoCompression
//   - CompressBestSpeed
//   - CompressBestCompression
//   - CompressDefaultCompression
//   - CompressHuffmanOnly
func ( RequestHandler, ,  int) RequestHandler {
	return func( *RequestCtx) {
		()
		switch {
		case .Request.Header.HasAcceptEncodingBytes(strBr):
			.Response.brotliBody() //nolint:errcheck
		case .Request.Header.HasAcceptEncodingBytes(strGzip):
			.Response.gzipBody() //nolint:errcheck
		case .Request.Header.HasAcceptEncodingBytes(strDeflate):
			.Response.deflateBody() //nolint:errcheck
		}
	}
}

// RequestCtx contains incoming request and manages outgoing response.
//
// It is forbidden copying RequestCtx instances.
//
// RequestHandler should avoid holding references to incoming RequestCtx and/or
// its members after the return.
// If holding RequestCtx references after the return is unavoidable
// (for instance, ctx is passed to a separate goroutine and ctx lifetime cannot
// be controlled), then the RequestHandler MUST call ctx.TimeoutError()
// before return.
//
// It is unsafe modifying/reading RequestCtx instance from concurrently
// running goroutines. The only exception is TimeoutError*, which may be called
// while other goroutines accessing RequestCtx.
type RequestCtx struct {
	noCopy noCopy

	// Incoming request.
	//
	// Copying Request by value is forbidden. Use pointer to Request instead.
	Request Request

	// Outgoing response.
	//
	// Copying Response by value is forbidden. Use pointer to Response instead.
	Response Response

	userValues userData

	connID         uint64
	connRequestNum uint64
	connTime       time.Time
	remoteAddr     net.Addr

	time time.Time

	logger ctxLogger
	s      *Server
	c      net.Conn
	fbr    firstByteReader

	timeoutResponse *Response
	timeoutCh       chan struct{}
	timeoutTimer    *time.Timer

	hijackHandler    HijackHandler
	hijackNoResponse bool
	formValueFunc    FormValueFunc
}

// HijackHandler must process the hijacked connection c.
//
// If KeepHijackedConns is disabled, which is by default,
// the connection c is automatically closed after returning from HijackHandler.
//
// The connection c must not be used after returning from the handler, if KeepHijackedConns is disabled.
//
// When KeepHijackedConns enabled, fasthttp will not Close() the connection,
// you must do it when you need it. You must not use c in any way after calling Close().
type HijackHandler func(c net.Conn)

// Hijack registers the given handler for connection hijacking.
//
// The handler is called after returning from RequestHandler
// and sending http response. The current connection is passed
// to the handler. The connection is automatically closed after
// returning from the handler.
//
// The server skips calling the handler in the following cases:
//
//   - 'Connection: close' header exists in either request or response.
//   - Unexpected error during response writing to the connection.
//
// The server stops processing requests from hijacked connections.
//
// Server limits such as Concurrency, ReadTimeout, WriteTimeout, etc.
// aren't applied to hijacked connections.
//
// The handler must not retain references to ctx members.
//
// Arbitrary 'Connection: Upgrade' protocols may be implemented
// with HijackHandler. For instance,
//
//   - WebSocket ( https://en.wikipedia.org/wiki/WebSocket )
//   - HTTP/2.0 ( https://en.wikipedia.org/wiki/HTTP/2 )
func ( *RequestCtx) ( HijackHandler) {
	.hijackHandler = 
}

// HijackSetNoResponse changes the behavior of hijacking a request.
// If HijackSetNoResponse is called with false fasthttp will send a response
// to the client before calling the HijackHandler (default). If HijackSetNoResponse
// is called with true no response is send back before calling the
// HijackHandler supplied in the Hijack function.
func ( *RequestCtx) ( bool) {
	.hijackNoResponse = 
}

// Hijacked returns true after Hijack is called.
func ( *RequestCtx) () bool {
	return .hijackHandler != nil
}

// SetUserValue stores the given value (arbitrary object)
// under the given key in ctx.
//
// The value stored in ctx may be obtained by UserValue*.
//
// This functionality may be useful for passing arbitrary values between
// functions involved in request processing.
//
// All the values are removed from ctx after returning from the top
// RequestHandler. Additionally, Close method is called on each value
// implementing io.Closer before removing the value from ctx.
func ( *RequestCtx) ( interface{},  interface{}) {
	.userValues.Set(, )
}

// SetUserValueBytes stores the given value (arbitrary object)
// under the given key in ctx.
//
// The value stored in ctx may be obtained by UserValue*.
//
// This functionality may be useful for passing arbitrary values between
// functions involved in request processing.
//
// All the values stored in ctx are deleted after returning from RequestHandler.
func ( *RequestCtx) ( []byte,  interface{}) {
	.userValues.SetBytes(, )
}

// UserValue returns the value stored via SetUserValue* under the given key.
func ( *RequestCtx) ( interface{}) interface{} {
	return .userValues.Get()
}

// UserValueBytes returns the value stored via SetUserValue*
// under the given key.
func ( *RequestCtx) ( []byte) interface{} {
	return .userValues.GetBytes()
}

// VisitUserValues calls visitor for each existing userValue with a key that is a string or []byte.
//
// visitor must not retain references to key and value after returning.
// Make key and/or value copies if you need storing them after returning.
func ( *RequestCtx) ( func([]byte, interface{})) {
	for ,  := 0, len(.userValues);  < ; ++ {
		 := &.userValues[]
		if ,  := .key.(string);  {
			(s2b(.key.(string)), .value)
		}
	}
}

// VisitUserValuesAll calls visitor for each existing userValue.
//
// visitor must not retain references to key and value after returning.
// Make key and/or value copies if you need storing them after returning.
func ( *RequestCtx) ( func(interface{}, interface{})) {
	for ,  := 0, len(.userValues);  < ; ++ {
		 := &.userValues[]
		(.key, .value)
	}
}

// ResetUserValues allows to reset user values from Request Context
func ( *RequestCtx) () {
	.userValues.Reset()
}

// RemoveUserValue removes the given key and the value under it in ctx.
func ( *RequestCtx) ( interface{}) {
	.userValues.Remove()
}

// RemoveUserValueBytes removes the given key and the value under it in ctx.
func ( *RequestCtx) ( []byte) {
	.userValues.RemoveBytes()
}

type connTLSer interface {
	Handshake() error
	ConnectionState() tls.ConnectionState
}

// IsTLS returns true if the underlying connection is tls.Conn.
//
// tls.Conn is an encrypted connection (aka SSL, HTTPS).
func ( *RequestCtx) () bool {
	// cast to (connTLSer) instead of (*tls.Conn), since it catches
	// cases with overridden tls.Conn such as:
	//
	// type customConn struct {
	//     *tls.Conn
	//
	//     // other custom fields here
	// }

	// perIPConn wraps the net.Conn in the Conn field
	if ,  := .c.(*perIPConn);  {
		,  := .Conn.(connTLSer)
		return 
	}

	,  := .c.(connTLSer)
	return 
}

// TLSConnectionState returns TLS connection state.
//
// The function returns nil if the underlying connection isn't tls.Conn.
//
// The returned state may be used for verifying TLS version, client certificates,
// etc.
func ( *RequestCtx) () *tls.ConnectionState {
	,  := .c.(connTLSer)
	if ! {
		return nil
	}
	 := .ConnectionState()
	return &
}

// Conn returns a reference to the underlying net.Conn.
//
// WARNING: Only use this method if you know what you are doing!
//
// Reading from or writing to the returned connection will end badly!
func ( *RequestCtx) () net.Conn {
	return .c
}

func ( *RequestCtx) () {
	.userValues.Reset()
	.Request.Reset()
	.Response.Reset()
	.fbr.reset()

	.connID = 0
	.connRequestNum = 0
	.connTime = zeroTime
	.remoteAddr = nil
	.time = zeroTime
	.c = nil

	// Don't reset ctx.s!
	// We have a pool per server so the next time this ctx is used it
	// will be assigned the same value again.
	// ctx might still be in use for context.Done() and context.Err()
	// which are safe to use as they only use ctx.s and no other value.

	if .timeoutResponse != nil {
		.timeoutResponse.Reset()
	}

	if .timeoutTimer != nil {
		stopTimer(.timeoutTimer)
	}

	.hijackHandler = nil
	.hijackNoResponse = false
}

type firstByteReader struct {
	c        net.Conn
	ch       byte
	byteRead bool
}

func ( *firstByteReader) () {
	.c = nil
	.ch = 0
	.byteRead = false
}

func ( *firstByteReader) ( []byte) (int, error) {
	if len() == 0 {
		return 0, nil
	}
	 := 0
	if !.byteRead {
		[0] = .ch
		 = [1:]
		.byteRead = true
		 = 1
	}
	,  := .c.Read()
	return  + , 
}

// Logger is used for logging formatted messages.
type Logger interface {
	// Printf must have the same semantics as log.Printf.
	Printf(format string, args ...interface{})
}

var ctxLoggerLock sync.Mutex

type ctxLogger struct {
	ctx    *RequestCtx
	logger Logger
}

func ( *ctxLogger) ( string,  ...interface{}) {
	 := fmt.Sprintf(, ...)
	ctxLoggerLock.Lock()
	.logger.Printf("%.3f %s - %s", time.Since(.ctx.ConnTime()).Seconds(), .ctx.String(), )
	ctxLoggerLock.Unlock()
}

var zeroTCPAddr = &net.TCPAddr{
	IP: net.IPv4zero,
}

// String returns unique string representation of the ctx.
//
// The returned value may be useful for logging.
func ( *RequestCtx) () string {
	return fmt.Sprintf("#%016X - %s<->%s - %s %s", .ID(), .LocalAddr(), .RemoteAddr(), .Request.Header.Method(), .URI().FullURI())
}

// ID returns unique ID of the request.
func ( *RequestCtx) () uint64 {
	return (.connID << 32) | .connRequestNum
}

// ConnID returns unique connection ID.
//
// This ID may be used to match distinct requests to the same incoming
// connection.
func ( *RequestCtx) () uint64 {
	return .connID
}

// Time returns RequestHandler call time.
func ( *RequestCtx) () time.Time {
	return .time
}

// ConnTime returns the time the server started serving the connection
// the current request came from.
func ( *RequestCtx) () time.Time {
	return .connTime
}

// ConnRequestNum returns request sequence number
// for the current connection.
//
// Sequence starts with 1.
func ( *RequestCtx) () uint64 {
	return .connRequestNum
}

// SetConnectionClose sets 'Connection: close' response header and closes
// connection after the RequestHandler returns.
func ( *RequestCtx) () {
	.Response.SetConnectionClose()
}

// SetStatusCode sets response status code.
func ( *RequestCtx) ( int) {
	.Response.SetStatusCode()
}

// SetContentType sets response Content-Type.
func ( *RequestCtx) ( string) {
	.Response.Header.SetContentType()
}

// SetContentTypeBytes sets response Content-Type.
//
// It is safe modifying contentType buffer after function return.
func ( *RequestCtx) ( []byte) {
	.Response.Header.SetContentTypeBytes()
}

// RequestURI returns RequestURI.
//
// The returned bytes are valid until your request handler returns.
func ( *RequestCtx) () []byte {
	return .Request.Header.RequestURI()
}

// URI returns requested uri.
//
// This uri is valid until your request handler returns.
func ( *RequestCtx) () *URI {
	return .Request.URI()
}

// Referer returns request referer.
//
// The returned bytes are valid until your request handler returns.
func ( *RequestCtx) () []byte {
	return .Request.Header.Referer()
}

// UserAgent returns User-Agent header value from the request.
//
// The returned bytes are valid until your request handler returns.
func ( *RequestCtx) () []byte {
	return .Request.Header.UserAgent()
}

// Path returns requested path.
//
// The returned bytes are valid until your request handler returns.
func ( *RequestCtx) () []byte {
	return .URI().Path()
}

// Host returns requested host.
//
// The returned bytes are valid until your request handler returns.
func ( *RequestCtx) () []byte {
	return .URI().Host()
}

// QueryArgs returns query arguments from RequestURI.
//
// It doesn't return POST'ed arguments - use PostArgs() for this.
//
// See also PostArgs, FormValue and FormFile.
//
// These args are valid until your request handler returns.
func ( *RequestCtx) () *Args {
	return .URI().QueryArgs()
}

// PostArgs returns POST arguments.
//
// It doesn't return query arguments from RequestURI - use QueryArgs for this.
//
// See also QueryArgs, FormValue and FormFile.
//
// These args are valid until your request handler returns.
func ( *RequestCtx) () *Args {
	return .Request.PostArgs()
}

// MultipartForm returns request's multipart form.
//
// Returns ErrNoMultipartForm if request's content-type
// isn't 'multipart/form-data'.
//
// All uploaded temporary files are automatically deleted after
// returning from RequestHandler. Either move or copy uploaded files
// into new place if you want retaining them.
//
// Use SaveMultipartFile function for permanently saving uploaded file.
//
// The returned form is valid until your request handler returns.
//
// See also FormFile and FormValue.
func ( *RequestCtx) () (*multipart.Form, error) {
	return .Request.MultipartForm()
}

// FormFile returns uploaded file associated with the given multipart form key.
//
// The file is automatically deleted after returning from RequestHandler,
// so either move or copy uploaded file into new place if you want retaining it.
//
// Use SaveMultipartFile function for permanently saving uploaded file.
//
// The returned file header is valid until your request handler returns.
func ( *RequestCtx) ( string) (*multipart.FileHeader, error) {
	,  := .MultipartForm()
	if  != nil {
		return nil, 
	}
	if .File == nil {
		return nil, 
	}
	 := .File[]
	if  == nil {
		return nil, ErrMissingFile
	}
	return [0], nil
}

// ErrMissingFile may be returned from FormFile when the is no uploaded file
// associated with the given multipart form key.
var ErrMissingFile = errors.New("there is no uploaded file associated with the given key")

// SaveMultipartFile saves multipart file fh under the given filename path.
func ( *multipart.FileHeader,  string) ( error) {
	var (
		  multipart.File
		 *os.File
	)
	,  = .Open()
	if  != nil {
		return
	}

	var  bool
	if ,  = .(*os.File);  {
		// Windows can't rename files that are opened.
		if  = .Close();  != nil {
			return
		}

		// If renaming fails we try the normal copying method.
		// Renaming could fail if the files are on different devices.
		if os.Rename(.Name(), ) == nil {
			return nil
		}

		// Reopen f for the code below.
		if ,  = .Open();  != nil {
			return
		}
	}

	defer func() {
		 := .Close()
		if  == nil {
			 = 
		}
	}()

	if ,  = os.Create();  != nil {
		return
	}
	defer func() {
		 := .Close()
		if  == nil {
			 = 
		}
	}()
	_,  = copyZeroAlloc(, )
	return
}

// FormValue returns form value associated with the given key.
//
// The value is searched in the following places:
//
//   - Query string.
//   - POST or PUT body.
//
// There are more fine-grained methods for obtaining form values:
//
//   - QueryArgs for obtaining values from query string.
//   - PostArgs for obtaining values from POST or PUT body.
//   - MultipartForm for obtaining values from multipart form.
//   - FormFile for obtaining uploaded files.
//
// The returned value is valid until your request handler returns.
func ( *RequestCtx) ( string) []byte {
	if .formValueFunc != nil {
		return .formValueFunc(, )
	}
	return defaultFormValue(, )
}

type FormValueFunc func(*RequestCtx, string) []byte

var (
	defaultFormValue = func( *RequestCtx,  string) []byte {
		 := .QueryArgs().Peek()
		if len() > 0 {
			return 
		}
		 = .PostArgs().Peek()
		if len() > 0 {
			return 
		}
		,  := .MultipartForm()
		if  == nil && .Value != nil {
			 := .Value[]
			if len() > 0 {
				return []byte([0])
			}
		}
		return nil
	}

	// NetHttpFormValueFunc gives consistent behavior with net/http. POST and PUT body parameters take precedence over URL query string values.
	NetHttpFormValueFunc = func( *RequestCtx,  string) []byte {
		 := .PostArgs().Peek()
		if len() > 0 {
			return 
		}
		,  := .MultipartForm()
		if  == nil && .Value != nil {
			 := .Value[]
			if len() > 0 {
				return []byte([0])
			}
		}
		 = .QueryArgs().Peek()
		if len() > 0 {
			return 
		}
		return nil
	}
)

// IsGet returns true if request method is GET.
func ( *RequestCtx) () bool {
	return .Request.Header.IsGet()
}

// IsPost returns true if request method is POST.
func ( *RequestCtx) () bool {
	return .Request.Header.IsPost()
}

// IsPut returns true if request method is PUT.
func ( *RequestCtx) () bool {
	return .Request.Header.IsPut()
}

// IsDelete returns true if request method is DELETE.
func ( *RequestCtx) () bool {
	return .Request.Header.IsDelete()
}

// IsConnect returns true if request method is CONNECT.
func ( *RequestCtx) () bool {
	return .Request.Header.IsConnect()
}

// IsOptions returns true if request method is OPTIONS.
func ( *RequestCtx) () bool {
	return .Request.Header.IsOptions()
}

// IsTrace returns true if request method is TRACE.
func ( *RequestCtx) () bool {
	return .Request.Header.IsTrace()
}

// IsPatch returns true if request method is PATCH.
func ( *RequestCtx) () bool {
	return .Request.Header.IsPatch()
}

// Method return request method.
//
// Returned value is valid until your request handler returns.
func ( *RequestCtx) () []byte {
	return .Request.Header.Method()
}

// IsHead returns true if request method is HEAD.
func ( *RequestCtx) () bool {
	return .Request.Header.IsHead()
}

// RemoteAddr returns client address for the given request.
//
// Always returns non-nil result.
func ( *RequestCtx) () net.Addr {
	if .remoteAddr != nil {
		return .remoteAddr
	}
	if .c == nil {
		return zeroTCPAddr
	}
	 := .c.RemoteAddr()
	if  == nil {
		return zeroTCPAddr
	}
	return 
}

// SetRemoteAddr sets remote address to the given value.
//
// Set nil value to restore default behaviour for using
// connection remote address.
func ( *RequestCtx) ( net.Addr) {
	.remoteAddr = 
}

// LocalAddr returns server address for the given request.
//
// Always returns non-nil result.
func ( *RequestCtx) () net.Addr {
	if .c == nil {
		return zeroTCPAddr
	}
	 := .c.LocalAddr()
	if  == nil {
		return zeroTCPAddr
	}
	return 
}

// RemoteIP returns the client ip the request came from.
//
// Always returns non-nil result.
func ( *RequestCtx) () net.IP {
	return addrToIP(.RemoteAddr())
}

// LocalIP returns the server ip the request came to.
//
// Always returns non-nil result.
func ( *RequestCtx) () net.IP {
	return addrToIP(.LocalAddr())
}

func addrToIP( net.Addr) net.IP {
	,  := .(*net.TCPAddr)
	if ! {
		return net.IPv4zero
	}
	return .IP
}

// Error sets response status code to the given value and sets response body
// to the given message.
//
// Warning: this will reset the response headers and body already set!
func ( *RequestCtx) ( string,  int) {
	.Response.Reset()
	.SetStatusCode()
	.SetContentTypeBytes(defaultContentType)
	.SetBodyString()
}

// Success sets response Content-Type and body to the given values.
func ( *RequestCtx) ( string,  []byte) {
	.SetContentType()
	.SetBody()
}

// SuccessString sets response Content-Type and body to the given values.
func ( *RequestCtx) (,  string) {
	.SetContentType()
	.SetBodyString()
}

// Redirect sets 'Location: uri' response header and sets the given statusCode.
//
// statusCode must have one of the following values:
//
//   - StatusMovedPermanently (301)
//   - StatusFound (302)
//   - StatusSeeOther (303)
//   - StatusTemporaryRedirect (307)
//   - StatusPermanentRedirect (308)
//
// All other statusCode values are replaced by StatusFound (302).
//
// The redirect uri may be either absolute or relative to the current
// request uri. Fasthttp will always send an absolute uri back to the client.
// To send a relative uri you can use the following code:
//
//	strLocation = []byte("Location") // Put this with your top level var () declarations.
//	ctx.Response.Header.SetCanonical(strLocation, "/relative?uri")
//	ctx.Response.SetStatusCode(fasthttp.StatusMovedPermanently)
func ( *RequestCtx) ( string,  int) {
	 := AcquireURI()
	.URI().CopyTo()
	.Update()
	.redirect(.FullURI(), )
	ReleaseURI()
}

// RedirectBytes sets 'Location: uri' response header and sets
// the given statusCode.
//
// statusCode must have one of the following values:
//
//   - StatusMovedPermanently (301)
//   - StatusFound (302)
//   - StatusSeeOther (303)
//   - StatusTemporaryRedirect (307)
//   - StatusPermanentRedirect (308)
//
// All other statusCode values are replaced by StatusFound (302).
//
// The redirect uri may be either absolute or relative to the current
// request uri. Fasthttp will always send an absolute uri back to the client.
// To send a relative uri you can use the following code:
//
//	strLocation = []byte("Location") // Put this with your top level var () declarations.
//	ctx.Response.Header.SetCanonical(strLocation, "/relative?uri")
//	ctx.Response.SetStatusCode(fasthttp.StatusMovedPermanently)
func ( *RequestCtx) ( []byte,  int) {
	 := b2s()
	.Redirect(, )
}

func ( *RequestCtx) ( []byte,  int) {
	.Response.Header.setNonSpecial(strLocation, )
	 = getRedirectStatusCode()
	.Response.SetStatusCode()
}

func getRedirectStatusCode( int) int {
	if  == StatusMovedPermanently ||  == StatusFound ||
		 == StatusSeeOther ||  == StatusTemporaryRedirect ||
		 == StatusPermanentRedirect {
		return 
	}
	return StatusFound
}

// SetBody sets response body to the given value.
//
// It is safe re-using body argument after the function returns.
func ( *RequestCtx) ( []byte) {
	.Response.SetBody()
}

// SetBodyString sets response body to the given value.
func ( *RequestCtx) ( string) {
	.Response.SetBodyString()
}

// ResetBody resets response body contents.
func ( *RequestCtx) () {
	.Response.ResetBody()
}

// SendFile sends local file contents from the given path as response body.
//
// This is a shortcut to ServeFile(ctx, path).
//
// SendFile logs all the errors via ctx.Logger.
//
// See also ServeFile, FSHandler and FS.
//
// WARNING: do not pass any user supplied paths to this function!
// WARNING: if path is based on user input users will be able to request
// any file on your filesystem! Use fasthttp.FS with a sane Root instead.
func ( *RequestCtx) ( string) {
	ServeFile(, )
}

// SendFileBytes sends local file contents from the given path as response body.
//
// This is a shortcut to ServeFileBytes(ctx, path).
//
// SendFileBytes logs all the errors via ctx.Logger.
//
// See also ServeFileBytes, FSHandler and FS.
//
// WARNING: do not pass any user supplied paths to this function!
// WARNING: if path is based on user input users will be able to request
// any file on your filesystem! Use fasthttp.FS with a sane Root instead.
func ( *RequestCtx) ( []byte) {
	ServeFileBytes(, )
}

// IfModifiedSince returns true if lastModified exceeds 'If-Modified-Since'
// value from the request header.
//
// The function returns true also 'If-Modified-Since' request header is missing.
func ( *RequestCtx) ( time.Time) bool {
	 := .Request.Header.peek(strIfModifiedSince)
	if len() == 0 {
		return true
	}
	,  := ParseHTTPDate()
	if  != nil {
		return true
	}
	 = .Truncate(time.Second)
	return .Before()
}

// NotModified resets response and sets '304 Not Modified' response status code.
func ( *RequestCtx) () {
	.Response.Reset()
	.SetStatusCode(StatusNotModified)
}

// NotFound resets response and sets '404 Not Found' response status code.
func ( *RequestCtx) () {
	.Response.Reset()
	.SetStatusCode(StatusNotFound)
	.SetBodyString("404 Page not found")
}

// Write writes p into response body.
func ( *RequestCtx) ( []byte) (int, error) {
	.Response.AppendBody()
	return len(), nil
}

// WriteString appends s to response body.
func ( *RequestCtx) ( string) (int, error) {
	.Response.AppendBodyString()
	return len(), nil
}

// PostBody returns POST request body.
//
// The returned bytes are valid until your request handler returns.
func ( *RequestCtx) () []byte {
	return .Request.Body()
}

// SetBodyStream sets response body stream and, optionally body size.
//
// bodyStream.Close() is called after finishing reading all body data
// if it implements io.Closer.
//
// If bodySize is >= 0, then bodySize bytes must be provided by bodyStream
// before returning io.EOF.
//
// If bodySize < 0, then bodyStream is read until io.EOF.
//
// See also SetBodyStreamWriter.
func ( *RequestCtx) ( io.Reader,  int) {
	.Response.SetBodyStream(, )
}

// SetBodyStreamWriter registers the given stream writer for populating
// response body.
//
// Access to RequestCtx and/or its members is forbidden from sw.
//
// This function may be used in the following cases:
//
//   - if response body is too big (more than 10MB).
//   - if response body is streamed from slow external sources.
//   - if response body must be streamed to the client in chunks.
//     (aka `http server push`).
func ( *RequestCtx) ( StreamWriter) {
	.Response.SetBodyStreamWriter()
}

// IsBodyStream returns true if response body is set via SetBodyStream*.
func ( *RequestCtx) () bool {
	return .Response.IsBodyStream()
}

// Logger returns logger, which may be used for logging arbitrary
// request-specific messages inside RequestHandler.
//
// Each message logged via returned logger contains request-specific information
// such as request id, request duration, local address, remote address,
// request method and request url.
//
// It is safe re-using returned logger for logging multiple messages
// for the current request.
//
// The returned logger is valid until your request handler returns.
func ( *RequestCtx) () Logger {
	if .logger.ctx == nil {
		.logger.ctx = 
	}
	if .logger.logger == nil {
		.logger.logger = .s.logger()
	}
	return &.logger
}

// TimeoutError sets response status code to StatusRequestTimeout and sets
// body to the given msg.
//
// All response modifications after TimeoutError call are ignored.
//
// TimeoutError MUST be called before returning from RequestHandler if there are
// references to ctx and/or its members in other goroutines remain.
//
// Usage of this function is discouraged. Prefer eliminating ctx references
// from pending goroutines instead of using this function.
func ( *RequestCtx) ( string) {
	.TimeoutErrorWithCode(, StatusRequestTimeout)
}

// TimeoutErrorWithCode sets response body to msg and response status
// code to statusCode.
//
// All response modifications after TimeoutErrorWithCode call are ignored.
//
// TimeoutErrorWithCode MUST be called before returning from RequestHandler
// if there are references to ctx and/or its members in other goroutines remain.
//
// Usage of this function is discouraged. Prefer eliminating ctx references
// from pending goroutines instead of using this function.
func ( *RequestCtx) ( string,  int) {
	var  Response
	.SetStatusCode()
	.SetBodyString()
	.TimeoutErrorWithResponse(&)
}

// TimeoutErrorWithResponse marks the ctx as timed out and sends the given
// response to the client.
//
// All ctx modifications after TimeoutErrorWithResponse call are ignored.
//
// TimeoutErrorWithResponse MUST be called before returning from RequestHandler
// if there are references to ctx and/or its members in other goroutines remain.
//
// Usage of this function is discouraged. Prefer eliminating ctx references
// from pending goroutines instead of using this function.
func ( *RequestCtx) ( *Response) {
	 := &Response{}
	.CopyTo()
	.timeoutResponse = 
}

// NextProto adds nph to be processed when key is negotiated when TLS
// connection is established.
//
// This function can only be called before the server is started.
func ( *Server) ( string,  ServeHandler) {
	if .nextProtos == nil {
		.nextProtos = make(map[string]ServeHandler)
	}

	.configTLS()
	.TLSConfig.NextProtos = append(.TLSConfig.NextProtos, )
	.nextProtos[] = 
}

func ( *Server) ( net.Conn) ( string,  error) {
	if ,  := .(connTLSer);  {
		if .ReadTimeout > 0 {
			if  := .SetReadDeadline(time.Now().Add(.ReadTimeout));  != nil {
				panic(fmt.Sprintf("BUG: error in SetReadDeadline(%v): %v", .ReadTimeout, ))
			}
		}

		if .WriteTimeout > 0 {
			if  := .SetWriteDeadline(time.Now().Add(.WriteTimeout));  != nil {
				panic(fmt.Sprintf("BUG: error in SetWriteDeadline(%v): %v", .WriteTimeout, ))
			}
		}

		 = .Handshake()
		if  == nil {
			 = .ConnectionState().NegotiatedProtocol
		}
	}
	return
}

// ListenAndServe serves HTTP requests from the given TCP4 addr.
//
// Pass custom listener to Serve if you need listening on non-TCP4 media
// such as IPv6.
//
// Accepted connections are configured to enable TCP keep-alives.
func ( *Server) ( string) error {
	,  := net.Listen("tcp4", )
	if  != nil {
		return 
	}
	return .Serve()
}

// ListenAndServeUNIX serves HTTP requests from the given UNIX addr.
//
// The function deletes existing file at addr before starting serving.
//
// The server sets the given file mode for the UNIX addr.
func ( *Server) ( string,  os.FileMode) error {
	if  := os.Remove();  != nil && !os.IsNotExist() {
		return fmt.Errorf("unexpected error when trying to remove unix socket file %q: %w", , )
	}
	,  := net.Listen("unix", )
	if  != nil {
		return 
	}
	if  = os.Chmod(, );  != nil {
		return fmt.Errorf("cannot chmod %#o for %q: %w", , , )
	}
	return .Serve()
}

// ListenAndServeTLS serves HTTPS requests from the given TCP4 addr.
//
// certFile and keyFile are paths to TLS certificate and key files.
//
// Pass custom listener to Serve if you need listening on non-TCP4 media
// such as IPv6.
//
// If the certFile or keyFile has not been provided to the server structure,
// the function will use the previously added TLS configuration.
//
// Accepted connections are configured to enable TCP keep-alives.
func ( *Server) (, ,  string) error {
	,  := net.Listen("tcp4", )
	if  != nil {
		return 
	}
	return .ServeTLS(, , )
}

// ListenAndServeTLSEmbed serves HTTPS requests from the given TCP4 addr.
//
// certData and keyData must contain valid TLS certificate and key data.
//
// Pass custom listener to Serve if you need listening on arbitrary media
// such as IPv6.
//
// If the certFile or keyFile has not been provided the server structure,
// the function will use previously added TLS configuration.
//
// Accepted connections are configured to enable TCP keep-alives.
func ( *Server) ( string, ,  []byte) error {
	,  := net.Listen("tcp4", )
	if  != nil {
		return 
	}
	return .ServeTLSEmbed(, , )
}

// ServeTLS serves HTTPS requests from the given listener.
//
// certFile and keyFile are paths to TLS certificate and key files.
//
// If the certFile or keyFile has not been provided the server structure,
// the function will use previously added TLS configuration.
func ( *Server) ( net.Listener, ,  string) error {
	.mu.Lock()
	.configTLS()
	 := len(.TLSConfig.Certificates) > 0 || .TLSConfig.GetCertificate != nil
	if ! ||  != "" ||  != "" {
		if  := .AppendCert(, );  != nil {
			.mu.Unlock()
			return 
		}
	}

	// BuildNameToCertificate has been deprecated since 1.14.
	// But since we also support older versions we'll keep this here.
	.TLSConfig.BuildNameToCertificate() //nolint:staticcheck

	.mu.Unlock()

	return .Serve(
		tls.NewListener(, .TLSConfig.Clone()),
	)
}

// ServeTLSEmbed serves HTTPS requests from the given listener.
//
// certData and keyData must contain valid TLS certificate and key data.
//
// If the certFile or keyFile has not been provided the server structure,
// the function will use previously added TLS configuration.
func ( *Server) ( net.Listener, ,  []byte) error {
	.mu.Lock()
	.configTLS()
	 := len(.TLSConfig.Certificates) > 0 || .TLSConfig.GetCertificate != nil
	if ! || len() != 0 || len() != 0 {
		if  := .AppendCertEmbed(, );  != nil {
			.mu.Unlock()
			return 
		}
	}

	// BuildNameToCertificate has been deprecated since 1.14.
	// But since we also support older versions we'll keep this here.
	.TLSConfig.BuildNameToCertificate() //nolint:staticcheck

	.mu.Unlock()

	return .Serve(
		tls.NewListener(, .TLSConfig.Clone()),
	)
}

// AppendCert appends certificate and keyfile to TLS Configuration.
//
// This function allows programmer to handle multiple domains
// in one server structure. See examples/multidomain
func ( *Server) (,  string) error {
	if len() == 0 && len() == 0 {
		return errNoCertOrKeyProvided
	}

	,  := tls.LoadX509KeyPair(, )
	if  != nil {
		return fmt.Errorf("cannot load TLS key pair from certFile=%q and keyFile=%q: %w", , , )
	}

	.configTLS()
	.TLSConfig.Certificates = append(.TLSConfig.Certificates, )

	return nil
}

// AppendCertEmbed does the same as AppendCert but using in-memory data.
func ( *Server) (,  []byte) error {
	if len() == 0 && len() == 0 {
		return errNoCertOrKeyProvided
	}

	,  := tls.X509KeyPair(, )
	if  != nil {
		return fmt.Errorf("cannot load TLS key pair from the provided certData(%d) and keyData(%d): %w",
			len(), len(), )
	}

	.configTLS()
	.TLSConfig.Certificates = append(.TLSConfig.Certificates, )

	return nil
}

func ( *Server) () {
	if .TLSConfig == nil {
		.TLSConfig = &tls.Config{}
	}
}

// DefaultConcurrency is the maximum number of concurrent connections
// the Server may serve by default (i.e. if Server.Concurrency isn't set).
const DefaultConcurrency = 256 * 1024

// Serve serves incoming connections from the given listener.
//
// Serve blocks until the given listener returns permanent error.
func ( *Server) ( net.Listener) error {
	var  time.Time
	var  time.Time
	var  net.Conn
	var  error

	 := .getConcurrency()

	.mu.Lock()
	.ln = append(.ln, )
	if .done == nil {
		.done = make(chan struct{})
	}
	if .concurrencyCh == nil {
		.concurrencyCh = make(chan struct{}, )
	}
	.mu.Unlock()

	 := &workerPool{
		WorkerFunc:            .serveConn,
		MaxWorkersCount:       ,
		LogAllErrors:          .LogAllErrors,
		MaxIdleWorkerDuration: .MaxIdleWorkerDuration,
		Logger:                .logger(),
		connState:             .setState,
	}
	.Start()

	// Count our waiting to accept a connection as an open connection.
	// This way we can't get into any weird state where just after accepting
	// a connection Shutdown is called which reads open as 0 because it isn't
	// incremented yet.
	atomic.AddInt32(&.open, 1)
	defer atomic.AddInt32(&.open, -1)

	for {
		if ,  = acceptConn(, , &);  != nil {
			.Stop()
			if  == io.EOF {
				return nil
			}
			return 
		}
		.setState(, StateNew)
		atomic.AddInt32(&.open, 1)
		if !.Serve() {
			atomic.AddInt32(&.open, -1)
			.writeFastError(, StatusServiceUnavailable,
				"The connection cannot be served because Server.Concurrency limit exceeded")
			.Close()
			.setState(, StateClosed)
			if time.Since() > time.Minute {
				.logger().Printf("The incoming connection cannot be served, because %d concurrent connections are served. "+
					"Try increasing Server.Concurrency", )
				 = time.Now()
			}

			// The current server reached concurrency limit,
			// so give other concurrently running servers a chance
			// accepting incoming connections on the same address.
			//
			// There is a hope other servers didn't reach their
			// concurrency limits yet :)
			//
			// See also: https://github.com/valyala/fasthttp/pull/485#discussion_r239994990
			if .SleepWhenConcurrencyLimitsExceeded > 0 {
				time.Sleep(.SleepWhenConcurrencyLimitsExceeded)
			}
		}
		 = nil
	}
}

// Shutdown gracefully shuts down the server without interrupting any active connections.
// Shutdown works by first closing all open listeners and then waiting indefinitely for all connections to return to idle and then shut down.
//
// When Shutdown is called, Serve, ListenAndServe, and ListenAndServeTLS immediately return nil.
// Make sure the program doesn't exit and waits instead for Shutdown to return.
//
// Shutdown does not close keepalive connections so it's recommended to set ReadTimeout and IdleTimeout to something else than 0.
func ( *Server) () error {
	return .ShutdownWithContext(context.Background())
}

// ShutdownWithContext gracefully shuts down the server without interrupting any active connections.
// ShutdownWithContext works by first closing all open listeners and then waiting for all connections to return to idle or context timeout and then shut down.
//
// When ShutdownWithContext is called, Serve, ListenAndServe, and ListenAndServeTLS immediately return nil.
// Make sure the program doesn't exit and waits instead for Shutdown to return.
//
// ShutdownWithContext does not close keepalive connections so it's recommended to set ReadTimeout and IdleTimeout to something else than 0.
func ( *Server) ( context.Context) ( error) {
	.mu.Lock()
	defer .mu.Unlock()

	atomic.StoreInt32(&.stop, 1)
	defer atomic.StoreInt32(&.stop, 0)

	if .ln == nil {
		return nil
	}

	for ,  := range .ln {
		if  = .Close();  != nil {
			return 
		}
	}

	if .done != nil {
		close(.done)
	}

	// Closing the listener will make Serve() call Stop on the worker pool.
	// Setting .stop to 1 will make serveConn() break out of its loop.
	// Now we just have to wait until all workers are done or timeout.
	 := time.NewTicker(time.Millisecond * 100)
	defer .Stop()
:
	for {
		.closeIdleConns()

		if  := atomic.LoadInt32(&.open);  == 0 {
			break
		}
		// This is not an optimal solution but using a sync.WaitGroup
		// here causes data races as it's hard to prevent Add() to be called
		// while Wait() is waiting.
		select {
		case <-.Done():
			 = .Err()
			break 
		case <-.C:
			continue
		}
	}

	.done = nil
	.ln = nil
	return 
}

func acceptConn( *Server,  net.Listener,  *time.Time) (net.Conn, error) {
	for {
		,  := .Accept()
		if  != nil {
			if ,  := .(net.Error);  && .Timeout() {
				.logger().Printf("Timeout error when accepting new connections: %v", )
				time.Sleep(time.Second)
				continue
			}
			if  != io.EOF && !strings.Contains(.Error(), "use of closed network connection") {
				.logger().Printf("Permanent error when accepting new connections: %v", )
				return nil, 
			}
			return nil, io.EOF
		}

		if ,  := .(*net.TCPConn);  && .TCPKeepalive {
			if  := .SetKeepAlive(.TCPKeepalive);  != nil {
				_ = .Close()
				return nil, 
			}
			if .TCPKeepalivePeriod > 0 {
				if  := .SetKeepAlivePeriod(.TCPKeepalivePeriod);  != nil {
					_ = .Close()
					return nil, 
				}
			}
		}

		if .MaxConnsPerIP > 0 {
			 := wrapPerIPConn(, )
			if  == nil {
				if time.Since(*) > time.Minute {
					.logger().Printf("The number of connections from %s exceeds MaxConnsPerIP=%d",
						getConnIP4(), .MaxConnsPerIP)
					* = time.Now()
				}
				continue
			}
			 = 
		}
		return , nil
	}
}

func wrapPerIPConn( *Server,  net.Conn) net.Conn {
	 := getUint32IP()
	if  == 0 {
		return 
	}
	 := .perIPConnCounter.Register()
	if  > .MaxConnsPerIP {
		.perIPConnCounter.Unregister()
		.writeFastError(, StatusTooManyRequests, "The number of connections from your ip exceeds MaxConnsPerIP")
		.Close()
		return nil
	}
	return acquirePerIPConn(, , &.perIPConnCounter)
}

var defaultLogger = Logger(log.New(os.Stderr, "", log.LstdFlags))

func ( *Server) () Logger {
	if .Logger != nil {
		return .Logger
	}
	return defaultLogger
}

var (
	// ErrPerIPConnLimit may be returned from ServeConn if the number of connections
	// per ip exceeds Server.MaxConnsPerIP.
	ErrPerIPConnLimit = errors.New("too many connections per ip")

	// ErrConcurrencyLimit may be returned from ServeConn if the number
	// of concurrently served connections exceeds Server.Concurrency.
	ErrConcurrencyLimit = errors.New("cannot serve the connection because Server.Concurrency concurrent connections are served")
)

// ServeConn serves HTTP requests from the given connection.
//
// ServeConn returns nil if all requests from the c are successfully served.
// It returns non-nil error otherwise.
//
// Connection c must immediately propagate all the data passed to Write()
// to the client. Otherwise requests' processing may hang.
//
// ServeConn closes c before returning.
func ( *Server) ( net.Conn) error {
	if .MaxConnsPerIP > 0 {
		 := wrapPerIPConn(, )
		if  == nil {
			return ErrPerIPConnLimit
		}
		 = 
	}

	 := atomic.AddUint32(&.concurrency, 1)
	if  > uint32(.getConcurrency()) {
		atomic.AddUint32(&.concurrency, ^uint32(0))
		.writeFastError(, StatusServiceUnavailable, "The connection cannot be served because Server.Concurrency limit exceeded")
		.Close()
		return ErrConcurrencyLimit
	}

	atomic.AddInt32(&.open, 1)

	 := .serveConn()

	atomic.AddUint32(&.concurrency, ^uint32(0))

	if  != errHijacked {
		 := .Close()
		.setState(, StateClosed)
		if  == nil {
			 = 
		}
	} else {
		 = nil
		.setState(, StateHijacked)
	}
	return 
}

var errHijacked = errors.New("connection has been hijacked")

// GetCurrentConcurrency returns a number of currently served
// connections.
//
// This function is intended be used by monitoring systems
func ( *Server) () uint32 {
	return atomic.LoadUint32(&.concurrency)
}

// GetOpenConnectionsCount returns a number of opened connections.
//
// This function is intended be used by monitoring systems
func ( *Server) () int32 {
	if atomic.LoadInt32(&.stop) == 0 {
		// Decrement by one to avoid reporting the extra open value that gets
		// counted while the server is listening.
		return atomic.LoadInt32(&.open) - 1
	}
	// This is not perfect, because s.stop could have changed to zero
	// before we load the value of s.open. However, in the common case
	// this avoids underreporting open connections by 1 during server shutdown.
	return atomic.LoadInt32(&.open)
}

func ( *Server) () int {
	 := .Concurrency
	if  <= 0 {
		 = DefaultConcurrency
	}
	return 
}

var globalConnID uint64

func nextConnID() uint64 {
	return atomic.AddUint64(&globalConnID, 1)
}

// DefaultMaxRequestBodySize is the maximum request body size the server
// reads by default.
//
// See Server.MaxRequestBodySize for details.
const DefaultMaxRequestBodySize = 4 * 1024 * 1024

func ( *Server) () time.Duration {
	if .IdleTimeout != 0 {
		return .IdleTimeout
	}
	return .ReadTimeout
}

func ( *Server) () {
	atomic.AddInt32(&.open, -1)
	atomic.AddUint32(&.concurrency, ^uint32(0))
}

func ( *Server) ( net.Conn) ( error) {
	defer .serveConnCleanup()
	atomic.AddUint32(&.concurrency, 1)

	var  string
	if ,  = .getNextProto();  != nil {
		return
	}
	if ,  := .nextProtos[];  {
		// Remove read or write deadlines that might have previously been set.
		// The next handler is responsible for setting its own deadlines.
		if .ReadTimeout > 0 || .WriteTimeout > 0 {
			if  := .SetDeadline(zeroTime);  != nil {
				panic(fmt.Sprintf("BUG: error in SetDeadline(zeroTime): %v", ))
			}
		}

		return ()
	}

	 := .getServerName()
	 := uint64(0)
	 := nextConnID()
	 := time.Now()
	 := .MaxRequestBodySize
	if  <= 0 {
		 = DefaultMaxRequestBodySize
	}
	 := .WriteTimeout
	 := time.Duration(0)

	 := .acquireCtx()
	.connTime = 
	 := .IsTLS()
	var (
		 *bufio.Reader
		 *bufio.Writer

		  *Response
		    HijackHandler
		 bool

		 bool

		 = true
	)
	for {
		++

		// If this is a keep-alive connection set the idle timeout.
		if  > 1 {
			if  := .idleTimeout();  > 0 {
				if  := .SetReadDeadline(time.Now().Add());  != nil {
					break
				}
			}
		}

		if !.ReduceMemoryUsage ||  != nil {
			if  == nil {
				 = acquireReader()
			}

			// If this is a keep-alive connection we want to try and read the first bytes
			// within the idle time.
			if  > 1 {
				var  []byte
				,  = .Peek(1)
				if len() == 0 {
					// If reading from a keep-alive connection returns nothing it means
					// the connection was closed (either timeout or from the other side).
					if  != io.EOF {
						 = ErrNothingRead{}
					}
				}
			}
		} else {
			// If this is a keep-alive connection acquireByteReader will try to peek
			// a couple of bytes already so the idle timeout will already be used.
			,  = acquireByteReader(&)
		}

		.Request.isTLS = 
		.Response.Header.noDefaultContentType = .NoDefaultContentType
		.Response.Header.noDefaultDate = .NoDefaultDate

		// Secure header error logs configuration
		.Request.Header.secureErrorLogMessage = .SecureErrorLogMessage
		.Response.Header.secureErrorLogMessage = .SecureErrorLogMessage
		.Request.secureErrorLogMessage = .SecureErrorLogMessage
		.Response.secureErrorLogMessage = .SecureErrorLogMessage

		if  == nil {
			.setState(, StateActive)

			if .ReadTimeout > 0 {
				if  := .SetReadDeadline(time.Now().Add(.ReadTimeout));  != nil {
					break
				}
			} else if .IdleTimeout > 0 &&  > 1 {
				// If this was an idle connection and the server has an IdleTimeout but
				// no ReadTimeout then we should remove the ReadTimeout.
				if  := .SetReadDeadline(zeroTime);  != nil {
					break
				}
			}
			if .DisableHeaderNamesNormalizing {
				.Request.Header.DisableNormalizing()
				.Response.Header.DisableNormalizing()
			}

			// Reading Headers.
			//
			// If we have pipeline response in the outgoing buffer,
			// we only want to try and read the next headers once.
			// If we have to wait for the next request we flush the
			// outgoing buffer first so it doesn't have to wait.
			if  != nil && .Buffered() > 0 {
				 = .Request.Header.readLoop(, false)
				if  == errNeedMore {
					 = .Flush()
					if  != nil {
						break
					}

					 = .Request.Header.Read()
				}
			} else {
				 = .Request.Header.Read()
			}

			if  == nil {
				if  := .HeaderReceived;  != nil {
					 := (&.Request.Header)
					if .ReadTimeout > 0 {
						 := time.Now().Add(.ReadTimeout)
						if  := .SetReadDeadline();  != nil {
							panic(fmt.Sprintf("BUG: error in SetReadDeadline(%v): %v", , ))
						}
					}
					switch {
					case .MaxRequestBodySize > 0:
						 = .MaxRequestBodySize
					case .MaxRequestBodySize > 0:
						 = .MaxRequestBodySize
					default:
						 = DefaultMaxRequestBodySize
					}
					if .WriteTimeout > 0 {
						 = .WriteTimeout
					} else {
						 = .WriteTimeout
					}
				}
				// read body
				if .StreamRequestBody {
					 = .Request.readBodyStream(, , .GetOnly, !.DisablePreParseMultipartForm)
				} else {
					 = .Request.readLimitBody(, , .GetOnly, !.DisablePreParseMultipartForm)
				}
			}

			if (.ReduceMemoryUsage && .Buffered() == 0) ||  != nil {
				releaseReader(, )
				 = nil
			}
		}

		if  != nil {
			if  == io.EOF {
				 = nil
			} else if ,  := .(ErrNothingRead);  {
				if  > 1 {
					// This is not the first request and we haven't read a single byte
					// of a new request yet. This means it's just a keep-alive connection
					// closing down either because the remote closed it or because
					// or a read timeout on our side. Either way just close the connection
					// and don't return any error response.
					 = nil
				} else {
					 = .error
				}
			}

			if  != nil {
				 = .writeErrorResponse(, , , )
			}
			break
		}

		// 'Expect: 100-continue' request handling.
		// See https://www.w3.org/Protocols/rfc2616/rfc2616-sec8.html#sec8.2.3 for details.
		if .Request.MayContinue() {

			// Allow the ability to deny reading the incoming request body
			if .ContinueHandler != nil {
				if  = .ContinueHandler(&.Request.Header); ! {
					if  != nil {
						.Reset(.c)
					}

					.SetStatusCode(StatusExpectationFailed)
				}
			}

			if  {
				if  == nil {
					 = acquireWriter()
				}

				// Send 'HTTP/1.1 100 Continue' response.
				_,  = .Write(strResponseContinue)
				if  != nil {
					break
				}
				 = .Flush()
				if  != nil {
					break
				}
				if .ReduceMemoryUsage {
					releaseWriter(, )
					 = nil
				}

				// Read request body.
				if  == nil {
					 = acquireReader()
				}

				if .StreamRequestBody {
					 = .Request.ContinueReadBodyStream(, , !.DisablePreParseMultipartForm)
				} else {
					 = .Request.ContinueReadBody(, , !.DisablePreParseMultipartForm)
				}
				if (.ReduceMemoryUsage && .Buffered() == 0) ||  != nil {
					releaseReader(, )
					 = nil
				}
				if  != nil {
					 = .writeErrorResponse(, , , )
					break
				}
			}
		}

		// store req.ConnectionClose so even if it was changed inside of handler
		 = .DisableKeepalive || .Request.Header.ConnectionClose()

		if  != "" {
			.Response.Header.SetServer()
		}
		.connID = 
		.connRequestNum = 
		.time = time.Now()

		// If a client denies a request the handler should not be called
		if  {
			.Handler()
		}

		 = .timeoutResponse
		if  != nil {
			// Acquire a new ctx because the old one will still be in use by the timeout out handler.
			 = .acquireCtx()
			.CopyTo(&.Response)
		}

		if .IsHead() {
			.Response.SkipBody = true
		}

		 = .hijackHandler
		.hijackHandler = nil
		 = .hijackNoResponse &&  != nil
		.hijackNoResponse = false

		if  > 0 {
			if  := .SetWriteDeadline(time.Now().Add());  != nil {
				panic(fmt.Sprintf("BUG: error in SetWriteDeadline(%v): %v", , ))
			}
			 = 
		} else if  > 0 {
			// We don't want a write timeout but we previously set one, remove it.
			if  := .SetWriteDeadline(zeroTime);  != nil {
				panic(fmt.Sprintf("BUG: error in SetWriteDeadline(zeroTime): %v", ))
			}
			 = 0
		}

		 =  ||
			(.MaxRequestsPerConn > 0 &&  >= uint64(.MaxRequestsPerConn)) ||
			.Response.Header.ConnectionClose() ||
			(.CloseOnShutdown && atomic.LoadInt32(&.stop) == 1)
		if  {
			.Response.Header.SetConnectionClose()
		} else if !.Request.Header.IsHTTP11() {
			// Set 'Connection: keep-alive' response header for HTTP/1.0 request.
			// There is no need in setting this header for http/1.1, since in http/1.1
			// connections are keep-alive by default.
			.Response.Header.setNonSpecial(strConnection, strKeepAlive)
		}

		if  != "" && len(.Response.Header.Server()) == 0 {
			.Response.Header.SetServer()
		}

		if ! {
			if  == nil {
				 = acquireWriter()
			}
			if  = writeResponse(, );  != nil {
				break
			}

			// Only flush the writer if we don't have another request in the pipeline.
			// This is a big of an ugly optimization for https://www.techempower.com/benchmarks/
			// This benchmark will send 16 pipelined requests. It is faster to pack as many responses
			// in a TCP packet and send it back at once than waiting for a flush every request.
			// In real world circumstances this behaviour could be argued as being wrong.
			if  == nil || .Buffered() == 0 ||  {
				 = .Flush()
				if  != nil {
					break
				}
			}
			if  {
				break
			}
			if .ReduceMemoryUsage &&  == nil {
				releaseWriter(, )
				 = nil
			}
		}

		if  != nil {
			var  io.Reader = 
			if  != nil {
				 = 
				 = nil
			}
			if  != nil {
				 = .Flush()
				if  != nil {
					break
				}
				releaseWriter(, )
				 = nil
			}
			 = .SetDeadline(zeroTime)
			if  != nil {
				break
			}
			go hijackConnHandler(, , , , )
			 = errHijacked
			break
		}

		if .Request.bodyStream != nil {
			if ,  := .Request.bodyStream.(*requestStream);  {
				releaseRequestStream()
			}
			.Request.bodyStream = nil
		}

		.setState(, StateIdle)
		.userValues.Reset()
		.Request.Reset()
		.Response.Reset()

		if atomic.LoadInt32(&.stop) == 1 {
			 = nil
			break
		}
	}

	if  != nil {
		releaseReader(, )
	}
	if  != nil {
		releaseWriter(, )
	}
	if  == nil {
		.releaseCtx()
	}

	return
}

func ( *Server) ( net.Conn,  ConnState) {
	.trackConn(, )
	if  := .ConnState;  != nil {
		(, )
	}
}

func hijackConnHandler( *RequestCtx,  io.Reader,  net.Conn,  *Server,  HijackHandler) {
	 := .acquireHijackConn(, )
	()

	if ,  := .(*bufio.Reader);  {
		releaseReader(, )
	}
	if !.KeepHijackedConns {
		.Close()
		.releaseHijackConn()
	}
	.releaseCtx()
}

func ( *Server) ( io.Reader,  net.Conn) *hijackConn {
	 := .hijackConnPool.Get()
	if  == nil {
		 := &hijackConn{
			Conn: ,
			r:    ,
			s:    ,
		}
		return 
	}
	 := .(*hijackConn)
	.Conn = 
	.r = 
	return 
}

func ( *Server) ( *hijackConn) {
	.Conn = nil
	.r = nil
	.hijackConnPool.Put()
}

type hijackConn struct {
	net.Conn
	r io.Reader
	s *Server
}

func ( *hijackConn) () net.Conn {
	return .Conn
}

func ( *hijackConn) ( []byte) (int, error) {
	return .r.Read()
}

func ( *hijackConn) () error {
	if !.s.KeepHijackedConns {
		// when we do not keep hijacked connections,
		// it is closed in hijackConnHandler.
		return nil
	}

	 := .Conn
	.s.releaseHijackConn()
	return .Close()
}

// LastTimeoutErrorResponse returns the last timeout response set
// via TimeoutError* call.
//
// This function is intended for custom server implementations.
func ( *RequestCtx) () *Response {
	return .timeoutResponse
}

func writeResponse( *RequestCtx,  *bufio.Writer) error {
	if .timeoutResponse != nil {
		return errors.New("cannot write timed out response")
	}
	 := .Response.Write()

	return 
}

const (
	defaultReadBufferSize  = 4096
	defaultWriteBufferSize = 4096
)

func acquireByteReader( **RequestCtx) (*bufio.Reader, error) {
	 := *
	 := .s
	 := .c
	.releaseCtx()

	// Make GC happy, so it could garbage collect ctx while we wait for the
	// next request.
	 = nil
	* = nil

	var  [1]byte
	,  := .Read([:])

	 = .acquireCtx()
	* = 
	if  != nil {
		// Treat all errors as EOF on unsuccessful read
		// of the first request byte.
		return nil, io.EOF
	}
	if  != 1 {
		// developer sanity-check
		panic("BUG: Reader must return at least one byte")
	}

	.fbr.c = 
	.fbr.ch = [0]
	.fbr.byteRead = false
	 := acquireReader()
	.Reset(&.fbr)
	return , nil
}

func acquireReader( *RequestCtx) *bufio.Reader {
	 := .s.readerPool.Get()
	if  == nil {
		 := .s.ReadBufferSize
		if  <= 0 {
			 = defaultReadBufferSize
		}
		return bufio.NewReaderSize(.c, )
	}
	 := .(*bufio.Reader)
	.Reset(.c)
	return 
}

func releaseReader( *Server,  *bufio.Reader) {
	.readerPool.Put()
}

func acquireWriter( *RequestCtx) *bufio.Writer {
	 := .s.writerPool.Get()
	if  == nil {
		 := .s.WriteBufferSize
		if  <= 0 {
			 = defaultWriteBufferSize
		}
		return bufio.NewWriterSize(.c, )
	}
	 := .(*bufio.Writer)
	.Reset(.c)
	return 
}

func releaseWriter( *Server,  *bufio.Writer) {
	.writerPool.Put()
}

func ( *Server) ( net.Conn) ( *RequestCtx) {
	 := .ctxPool.Get()
	if  == nil {
		 := !.ReduceMemoryUsage

		 = new(RequestCtx)
		.Request.keepBodyBuffer = 
		.Response.keepBodyBuffer = 
		.s = 
	} else {
		 = .(*RequestCtx)
	}
	if .FormValueFunc != nil {
		.formValueFunc = .FormValueFunc
	}
	.c = 

	return 
}

// Init2 prepares ctx for passing to RequestHandler.
//
// conn is used only for determining local and remote addresses.
//
// This function is intended for custom Server implementations.
// See https://github.com/valyala/httpteleport for details.
func ( *RequestCtx) ( net.Conn,  Logger,  bool) {
	.c = 
	.remoteAddr = nil
	.logger.logger = 
	.connID = nextConnID()
	.s = fakeServer
	.connRequestNum = 0
	.connTime = time.Now()

	 := !
	.Request.keepBodyBuffer = 
	.Response.keepBodyBuffer = 
}

// Init prepares ctx for passing to RequestHandler.
//
// remoteAddr and logger are optional. They are used by RequestCtx.Logger().
//
// This function is intended for custom Server implementations.
func ( *RequestCtx) ( *Request,  net.Addr,  Logger) {
	if  == nil {
		 = zeroTCPAddr
	}
	 := &fakeAddrer{
		laddr: zeroTCPAddr,
		raddr: ,
	}
	if  == nil {
		 = defaultLogger
	}
	.Init2(, , true)
	.CopyTo(&.Request)
}

// Deadline returns the time when work done on behalf of this context
// should be canceled. Deadline returns ok==false when no deadline is
// set. Successive calls to Deadline return the same results.
//
// This method always returns 0, false and is only present to make
// RequestCtx implement the context interface.
func ( *RequestCtx) () ( time.Time,  bool) {
	return
}

// Done returns a channel that's closed when work done on behalf of this
// context should be canceled. Done may return nil if this context can
// never be canceled. Successive calls to Done return the same value.
//
// Note: Because creating a new channel for every request is just too expensive, so
// RequestCtx.s.done is only closed when the server is shutting down
func ( *RequestCtx) () <-chan struct{} {
	return .s.done
}

// Err returns a non-nil error value after Done is closed,
// successive calls to Err return the same error.
// If Done is not yet closed, Err returns nil.
// If Done is closed, Err returns a non-nil error explaining why:
// Canceled if the context was canceled (via server Shutdown)
// or DeadlineExceeded if the context's deadline passed.
//
// Note: Because creating a new channel for every request is just too expensive, so
// RequestCtx.s.done is only closed when the server is shutting down
func ( *RequestCtx) () error {
	select {
	case <-.s.done:
		return context.Canceled
	default:
		return nil
	}
}

// Value returns the value associated with this context for key, or nil
// if no value is associated with key. Successive calls to Value with
// the same key returns the same result.
//
// This method is present to make RequestCtx implement the context interface.
// This method is the same as calling ctx.UserValue(key)
func ( *RequestCtx) ( interface{}) interface{} {
	return .UserValue()
}

var fakeServer = &Server{
	// Initialize concurrencyCh for TimeoutHandler
	concurrencyCh: make(chan struct{}, DefaultConcurrency),
}

type fakeAddrer struct {
	net.Conn
	laddr net.Addr
	raddr net.Addr
}

func ( *fakeAddrer) () net.Addr {
	return .raddr
}

func ( *fakeAddrer) () net.Addr {
	return .laddr
}

func ( *fakeAddrer) ( []byte) (int, error) {
	// developer sanity-check
	panic("BUG: unexpected Read call")
}

func ( *fakeAddrer) ( []byte) (int, error) {
	// developer sanity-check
	panic("BUG: unexpected Write call")
}

func ( *fakeAddrer) () error {
	// developer sanity-check
	panic("BUG: unexpected Close call")
}

func ( *Server) ( *RequestCtx) {
	if .timeoutResponse != nil {
		// developer sanity-check
		panic("BUG: cannot release timed out RequestCtx")
	}

	.reset()
	.ctxPool.Put()
}

func ( *Server) () string {
	 := .Name
	if  == "" {
		if !.NoDefaultServerHeader {
			 = defaultServerName
		}
	}
	return 
}

func ( *Server) ( io.Writer,  int,  string) {
	.Write(formatStatusLine(nil, strHTTP11, , s2b(StatusMessage()))) //nolint:errcheck

	 := .getServerName()
	if  != "" {
		 = fmt.Sprintf("Server: %s\r\n", )
	}
	 := ""
	if !.NoDefaultDate {
		serverDateOnce.Do(updateServerDate)
		 = fmt.Sprintf("Date: %s\r\n", serverDate.Load())
	}

	fmt.Fprintf(, "Connection: close\r\n"+
		+
		+
		"Content-Type: text/plain\r\n"+
		"Content-Length: %d\r\n"+
		"\r\n"+
		"%s",
		len(), )
}

func defaultErrorHandler( *RequestCtx,  error) {
	if ,  := .(*ErrSmallBuffer);  {
		.Error("Too big request header", StatusRequestHeaderFieldsTooLarge)
	} else if ,  := .(*net.OpError);  && .Timeout() {
		.Error("Request timeout", StatusRequestTimeout)
	} else {
		.Error("Error when parsing request", StatusBadRequest)
	}
}

func ( *Server) ( *bufio.Writer,  *RequestCtx,  string,  error) *bufio.Writer {
	 := defaultErrorHandler
	if .ErrorHandler != nil {
		 = .ErrorHandler
	}

	(, )

	if  != "" {
		.Response.Header.SetServer()
	}
	.SetConnectionClose()
	if  == nil {
		 = acquireWriter()
	}

	writeResponse(, ) //nolint:errcheck
	.Response.Reset()
	.Flush()

	return 
}

func ( *Server) ( net.Conn,  ConnState) {
	.idleConnsMu.Lock()
	switch  {
	case StateIdle:
		if .idleConns == nil {
			.idleConns = make(map[net.Conn]time.Time)
		}
		.idleConns[] = time.Now()
	case StateNew:
		if .idleConns == nil {
			.idleConns = make(map[net.Conn]time.Time)
		}
		// Count the connection as Idle after 5 seconds.
		// Same as net/http.Server: https://github.com/golang/go/blob/85d7bab91d9a3ed1f76842e4328973ea75efef54/src/net/http/server.go#L2834-L2836
		.idleConns[] = time.Now().Add(time.Second * 5)

	default:
		delete(.idleConns, )
	}
	.idleConnsMu.Unlock()
}

func ( *Server) () {
	.idleConnsMu.Lock()
	 := time.Now()
	for ,  := range .idleConns {
		if .Sub() >= 0 {
			_ = .Close()
			delete(.idleConns, )
		}
	}
	.idleConnsMu.Unlock()
}

// A ConnState represents the state of a client connection to a server.
// It's used by the optional Server.ConnState hook.
type ConnState int

const (
	// StateNew represents a new connection that is expected to
	// send a request immediately. Connections begin at this
	// state and then transition to either StateActive or
	// StateClosed.
	StateNew ConnState = iota

	// StateActive represents a connection that has read 1 or more
	// bytes of a request. The Server.ConnState hook for
	// StateActive fires before the request has entered a handler
	// and doesn't fire again until the request has been
	// handled. After the request is handled, the state
	// transitions to StateClosed, StateHijacked, or StateIdle.
	// For HTTP/2, StateActive fires on the transition from zero
	// to one active request, and only transitions away once all
	// active requests are complete. That means that ConnState
	// cannot be used to do per-request work; ConnState only notes
	// the overall state of the connection.
	StateActive

	// StateIdle represents a connection that has finished
	// handling a request and is in the keep-alive state, waiting
	// for a new request. Connections transition from StateIdle
	// to either StateActive or StateClosed.
	StateIdle

	// StateHijacked represents a hijacked connection.
	// This is a terminal state. It does not transition to StateClosed.
	StateHijacked

	// StateClosed represents a closed connection.
	// This is a terminal state. Hijacked connections do not
	// transition to StateClosed.
	StateClosed
)

var stateName = map[ConnState]string{
	StateNew:      "new",
	StateActive:   "active",
	StateIdle:     "idle",
	StateHijacked: "hijacked",
	StateClosed:   "closed",
}

func ( ConnState) () string {
	return stateName[]
}