Skip to main content

hyper/proto/h1/
conn.rs

1use std::fmt;
2#[cfg(feature = "server")]
3use std::future::Future;
4use std::io;
5use std::marker::{PhantomData, Unpin};
6use std::pin::Pin;
7use std::task::{Context, Poll};
8#[cfg(feature = "server")]
9use std::time::Duration;
10
11use crate::rt::{Read, Write};
12use bytes::{Buf, Bytes};
13use futures_core::ready;
14use http::header::{Entry, HeaderValue, CONNECTION};
15use http::{HeaderMap, Method, Version};
16use http_body::Frame;
17use httparse::ParserConfig;
18
19use super::io::Buffered;
20use super::{Decoder, Encode, EncodedBuf, Encoder, Http1Transaction, ParseContext, Wants};
21use crate::body::DecodedLength;
22#[cfg(feature = "server")]
23use crate::common::time::Time;
24use crate::headers;
25use crate::proto::{BodyLength, MessageHead};
26#[cfg(feature = "server")]
27use crate::rt::Sleep;
28
29const H2_PREFACE: &[u8] = b"PRI * HTTP/2.0\r\n\r\nSM\r\n\r\n";
30
31/// This handles a connection, which will have been established over an
32/// `Read + Write` (like a socket), and will likely include multiple
33/// `Transaction`s over HTTP.
34///
35/// The connection will determine when a message begins and ends as well as
36/// determine if this connection can be kept alive after the message,
37/// or if it is complete.
38pub(crate) struct Conn<I, B, T> {
39    io: Buffered<I, EncodedBuf<B>>,
40    state: State,
41    _marker: PhantomData<fn(T)>,
42}
43
44impl<I, B, T> Conn<I, B, T>
45where
46    I: Read + Write + Unpin,
47    B: Buf,
48    T: Http1Transaction,
49{
50    pub(crate) fn new(io: I) -> Conn<I, B, T> {
51        Conn {
52            io: Buffered::new(io),
53            state: State {
54                allow_half_close: false,
55                cached_headers: None,
56                error: None,
57                keep_alive: KA::Busy,
58                method: None,
59                h1_parser_config: ParserConfig::default(),
60                h1_max_headers: None,
61                h1_max_header_size: None,
62                #[cfg(feature = "server")]
63                h1_header_read_timeout: None,
64                #[cfg(feature = "server")]
65                h1_header_read_timeout_fut: None,
66                #[cfg(feature = "server")]
67                h1_header_read_timeout_running: false,
68                #[cfg(feature = "server")]
69                date_header: true,
70                #[cfg(feature = "server")]
71                timer: Time::Empty,
72                preserve_header_case: false,
73                #[cfg(feature = "ffi")]
74                preserve_header_order: false,
75                title_case_headers: false,
76                h09_responses: false,
77                #[cfg(feature = "client")]
78                on_informational: None,
79                notify_read: false,
80                reading: Reading::Init,
81                writing: Writing::Init,
82                upgrade: None,
83                // We assume a modern world where the remote speaks HTTP/1.1.
84                // If they tell us otherwise, we'll downgrade in `read_head`.
85                version: Version::HTTP_11,
86                allow_trailer_fields: false,
87            },
88            _marker: PhantomData,
89        }
90    }
91
92    #[cfg(feature = "server")]
93    pub(crate) fn set_timer(&mut self, timer: Time) {
94        self.state.timer = timer;
95    }
96
97    #[cfg(feature = "server")]
98    pub(crate) fn set_flush_pipeline(&mut self, enabled: bool) {
99        self.io.set_flush_pipeline(enabled);
100    }
101
102    pub(crate) fn set_write_strategy_queue(&mut self) {
103        self.io.set_write_strategy_queue();
104    }
105
106    pub(crate) fn set_max_buf_size(&mut self, max: usize) {
107        self.io.set_max_buf_size(max);
108    }
109
110    #[cfg(feature = "client")]
111    pub(crate) fn set_read_buf_exact_size(&mut self, sz: usize) {
112        self.io.set_read_buf_exact_size(sz);
113    }
114
115    pub(crate) fn set_write_strategy_flatten(&mut self) {
116        self.io.set_write_strategy_flatten();
117    }
118
119    pub(crate) fn set_h1_parser_config(&mut self, parser_config: ParserConfig) {
120        self.state.h1_parser_config = parser_config;
121    }
122
123    pub(crate) fn set_title_case_headers(&mut self) {
124        self.state.title_case_headers = true;
125    }
126
127    pub(crate) fn set_preserve_header_case(&mut self) {
128        self.state.preserve_header_case = true;
129    }
130
131    #[cfg(feature = "ffi")]
132    pub(crate) fn set_preserve_header_order(&mut self) {
133        self.state.preserve_header_order = true;
134    }
135
136    #[cfg(feature = "client")]
137    pub(crate) fn set_h09_responses(&mut self) {
138        self.state.h09_responses = true;
139    }
140
141    pub(crate) fn set_http1_max_headers(&mut self, val: usize) {
142        self.state.h1_max_headers = Some(val);
143    }
144
145    pub(crate) fn set_http1_max_header_size(&mut self, val: usize) {
146        self.state.h1_max_header_size = Some(val);
147    }
148
149    #[cfg(feature = "server")]
150    pub(crate) fn set_http1_header_read_timeout(&mut self, val: Duration) {
151        self.state.h1_header_read_timeout = Some(val);
152    }
153
154    #[cfg(feature = "server")]
155    pub(crate) fn set_allow_half_close(&mut self) {
156        self.state.allow_half_close = true;
157    }
158
159    #[cfg(feature = "server")]
160    pub(crate) fn disable_date_header(&mut self) {
161        self.state.date_header = false;
162    }
163
164    pub(crate) fn into_inner(self) -> (I, Bytes) {
165        self.io.into_inner()
166    }
167
168    pub(crate) fn pending_upgrade(&mut self) -> Option<crate::upgrade::Pending> {
169        self.state.upgrade.take()
170    }
171
172    pub(crate) fn is_read_closed(&self) -> bool {
173        self.state.is_read_closed()
174    }
175
176    pub(crate) fn is_write_closed(&self) -> bool {
177        self.state.is_write_closed()
178    }
179
180    pub(crate) fn can_read_head(&self) -> bool {
181        if !matches!(self.state.reading, Reading::Init) {
182            return false;
183        }
184
185        if T::should_read_first() {
186            return true;
187        }
188
189        !matches!(self.state.writing, Writing::Init)
190    }
191
192    pub(crate) fn can_read_body(&self) -> bool {
193        matches!(
194            self.state.reading,
195            Reading::Body(..) | Reading::Continue(..)
196        )
197    }
198
199    #[cfg(feature = "server")]
200    pub(crate) fn has_initial_read_write_state(&self) -> bool {
201        matches!(self.state.reading, Reading::Init)
202            && matches!(self.state.writing, Writing::Init)
203            && self.io.read_buf().is_empty()
204    }
205
206    fn should_error_on_eof(&self) -> bool {
207        // If we're idle, it's probably just the connection closing gracefully.
208        T::should_error_on_parse_eof() && !self.state.is_idle()
209    }
210
211    fn has_h2_prefix(&self) -> bool {
212        let read_buf = self.io.read_buf();
213        read_buf.len() >= 24 && read_buf[..24] == *H2_PREFACE
214    }
215
216    pub(super) fn poll_read_head(
217        &mut self,
218        cx: &mut Context<'_>,
219    ) -> Poll<Option<crate::Result<(MessageHead<T::Incoming>, DecodedLength, Wants)>>> {
220        debug_assert!(self.can_read_head());
221        trace!("Conn::read_head");
222
223        #[cfg(feature = "server")]
224        if !self.state.h1_header_read_timeout_running {
225            if let Some(h1_header_read_timeout) = self.state.h1_header_read_timeout {
226                let deadline = self.state.timer.now() + h1_header_read_timeout;
227                self.state.h1_header_read_timeout_running = true;
228                match &mut self.state.h1_header_read_timeout_fut {
229                    Some(h1_header_read_timeout_fut) => {
230                        trace!("resetting h1 header read timeout timer");
231                        self.state.timer.reset(h1_header_read_timeout_fut, deadline);
232                    }
233                    None => {
234                        trace!("setting h1 header read timeout timer");
235                        self.state.h1_header_read_timeout_fut =
236                            Some(self.state.timer.sleep_until(deadline));
237                    }
238                }
239            }
240        }
241
242        let msg = match self.io.parse::<T>(
243            cx,
244            ParseContext {
245                cached_headers: &mut self.state.cached_headers,
246                req_method: &mut self.state.method,
247                h1_parser_config: self.state.h1_parser_config.clone(),
248                h1_max_headers: self.state.h1_max_headers,
249                h1_max_header_size: self.state.h1_max_header_size,
250                preserve_header_case: self.state.preserve_header_case,
251                #[cfg(feature = "ffi")]
252                preserve_header_order: self.state.preserve_header_order,
253                h09_responses: self.state.h09_responses,
254                #[cfg(feature = "client")]
255                on_informational: &mut self.state.on_informational,
256            },
257        ) {
258            Poll::Ready(Ok(msg)) => msg,
259            Poll::Ready(Err(e)) => return self.on_read_head_error(e),
260            Poll::Pending => {
261                #[cfg(feature = "server")]
262                if self.state.h1_header_read_timeout_running {
263                    if let Some(h1_header_read_timeout_fut) =
264                        &mut self.state.h1_header_read_timeout_fut
265                    {
266                        if Pin::new(h1_header_read_timeout_fut).poll(cx).is_ready() {
267                            self.state.h1_header_read_timeout_running = false;
268
269                            warn!("read header from client timeout");
270                            return Poll::Ready(Some(Err(crate::Error::new_header_timeout())));
271                        }
272                    }
273                }
274
275                return Poll::Pending;
276            }
277        };
278
279        #[cfg(feature = "server")]
280        {
281            self.state.h1_header_read_timeout_running = false;
282            self.state.h1_header_read_timeout_fut = None;
283        }
284
285        // Note: don't deconstruct `msg` into local variables, it appears
286        // the optimizer doesn't remove the extra copies.
287
288        debug!("incoming body is {}", msg.decode);
289
290        // Prevent accepting HTTP/0.9 responses after the initial one, if any.
291        self.state.h09_responses = false;
292
293        // Drop any OnInformational callbacks, we're done there!
294        #[cfg(feature = "client")]
295        {
296            self.state.on_informational = None;
297        }
298
299        self.state.busy();
300        self.state.keep_alive &= msg.keep_alive;
301        self.state.version = msg.head.version;
302
303        let mut wants = if msg.wants_upgrade {
304            Wants::UPGRADE
305        } else {
306            Wants::EMPTY
307        };
308
309        if msg.decode == DecodedLength::ZERO {
310            if msg.expect_continue {
311                debug!("ignoring expect-continue since body is empty");
312            }
313            self.state.reading = Reading::KeepAlive;
314            if !T::should_read_first() {
315                self.try_keep_alive(cx);
316            }
317        } else if msg.expect_continue && msg.head.version.gt(&Version::HTTP_10) {
318            let h1_max_header_size = self.state.h1_max_header_size;
319            self.state.reading = Reading::Continue(Decoder::new(
320                msg.decode,
321                self.state.h1_max_headers,
322                h1_max_header_size,
323            ));
324            wants = wants.add(Wants::EXPECT);
325        } else {
326            let h1_max_header_size = self.state.h1_max_header_size;
327            self.state.reading = Reading::Body(Decoder::new(
328                msg.decode,
329                self.state.h1_max_headers,
330                h1_max_header_size,
331            ));
332        }
333
334        self.state.allow_trailer_fields = headers::te_is_trailers(&msg.head.headers);
335
336        Poll::Ready(Some(Ok((msg.head, msg.decode, wants))))
337    }
338
339    fn on_read_head_error<Z>(&mut self, e: crate::Error) -> Poll<Option<crate::Result<Z>>> {
340        // If we are currently waiting on a message, then an empty
341        // message should be reported as an error. If not, it is just
342        // the connection closing gracefully.
343        let must_error = self.should_error_on_eof();
344        self.close_read();
345        self.io.consume_leading_lines();
346        let was_mid_parse = e.is_parse() || !self.io.read_buf().is_empty();
347        if was_mid_parse || must_error {
348            // We check if the buf contains the h2 Preface
349            debug!(
350                "parse error ({}) with {} bytes",
351                e,
352                self.io.read_buf().len()
353            );
354            match self.on_parse_error(e) {
355                Ok(()) => Poll::Pending, // XXX: wat?
356                Err(e) => Poll::Ready(Some(Err(e))),
357            }
358        } else {
359            debug!("read eof");
360            self.close_write();
361            Poll::Ready(None)
362        }
363    }
364
365    pub(crate) fn poll_read_body(
366        &mut self,
367        cx: &mut Context<'_>,
368    ) -> Poll<Option<io::Result<Frame<Bytes>>>> {
369        debug_assert!(self.can_read_body());
370
371        let (reading, ret) = match &mut self.state.reading {
372            Reading::Body(decoder) => {
373                match ready!(decoder.decode(cx, &mut self.io)) {
374                    Ok(frame) => {
375                        if frame.is_data() {
376                            let slice = frame.data_ref().unwrap_or_else(|| unreachable!());
377                            let (reading, maybe_frame) = if decoder.is_eof() {
378                                debug!("incoming body completed");
379                                (
380                                    Reading::KeepAlive,
381                                    if !slice.is_empty() {
382                                        Some(Ok(frame))
383                                    } else {
384                                        None
385                                    },
386                                )
387                            } else if slice.is_empty() {
388                                error!("incoming body unexpectedly ended");
389                                // This should be unreachable, since all 3 decoders
390                                // either set eof=true or return an Err when reading
391                                // an empty slice...
392                                (Reading::Closed, None)
393                            } else {
394                                return Poll::Ready(Some(Ok(frame)));
395                            };
396                            (reading, Poll::Ready(maybe_frame))
397                        } else if frame.is_trailers() {
398                            debug!("incoming body completed with trailers");
399                            (Reading::KeepAlive, Poll::Ready(Some(Ok(frame))))
400                        } else {
401                            trace!("discarding unknown frame");
402                            (Reading::Closed, Poll::Ready(None))
403                        }
404                    }
405                    Err(e) => {
406                        debug!("incoming body decode error: {}", e);
407                        (Reading::Closed, Poll::Ready(Some(Err(e))))
408                    }
409                }
410            }
411            Reading::Continue(decoder) => {
412                // Write the 100 Continue if not already responded...
413                if let Writing::Init = self.state.writing {
414                    trace!("automatically sending 100 Continue");
415                    let cont = b"HTTP/1.1 100 Continue\r\n\r\n";
416                    self.io.headers_buf().extend_from_slice(cont);
417                }
418
419                // And now recurse once in the Reading::Body state...
420                self.state.reading = Reading::Body(decoder.clone());
421                return self.poll_read_body(cx);
422            }
423            _ => unreachable!("poll_read_body invalid state: {:?}", self.state.reading),
424        };
425
426        self.state.reading = reading;
427        self.try_keep_alive(cx);
428        ret
429    }
430
431    pub(crate) fn wants_read_again(&mut self) -> bool {
432        let ret = self.state.notify_read;
433        self.state.notify_read = false;
434        ret
435    }
436
437    pub(crate) fn poll_read_keep_alive(&mut self, cx: &mut Context<'_>) -> Poll<crate::Result<()>> {
438        debug_assert!(!self.can_read_head() && !self.can_read_body());
439
440        if self.is_read_closed() {
441            Poll::Pending
442        } else if self.is_mid_message() {
443            self.mid_message_detect_eof(cx)
444        } else {
445            self.require_empty_read(cx)
446        }
447    }
448
449    fn is_mid_message(&self) -> bool {
450        !matches!(
451            (&self.state.reading, &self.state.writing),
452            (&Reading::Init, &Writing::Init)
453        )
454    }
455
456    // This will check to make sure the io object read is empty.
457    //
458    // This should only be called for Clients wanting to enter the idle
459    // state.
460    fn require_empty_read(&mut self, cx: &mut Context<'_>) -> Poll<crate::Result<()>> {
461        debug_assert!(!self.can_read_head() && !self.can_read_body() && !self.is_read_closed());
462        debug_assert!(!self.is_mid_message());
463        debug_assert!(T::is_client());
464
465        if !self.io.read_buf().is_empty() {
466            debug!("received an unexpected {} bytes", self.io.read_buf().len());
467            return Poll::Ready(Err(crate::Error::new_unexpected_message()));
468        }
469
470        let num_read = ready!(self.force_io_read(cx)).map_err(crate::Error::new_io)?;
471
472        if num_read == 0 {
473            let ret = if self.should_error_on_eof() {
474                trace!("found unexpected EOF on busy connection: {:?}", self.state);
475                Poll::Ready(Err(crate::Error::new_incomplete()))
476            } else {
477                trace!("found EOF on idle connection, closing");
478                Poll::Ready(Ok(()))
479            };
480
481            // order is important: should_error needs state BEFORE close_read
482            self.state.close_read();
483            return ret;
484        }
485
486        debug!(
487            "received unexpected {} bytes on an idle connection",
488            num_read
489        );
490        Poll::Ready(Err(crate::Error::new_unexpected_message()))
491    }
492
493    fn mid_message_detect_eof(&mut self, cx: &mut Context<'_>) -> Poll<crate::Result<()>> {
494        debug_assert!(!self.can_read_head() && !self.can_read_body() && !self.is_read_closed());
495        debug_assert!(self.is_mid_message());
496
497        if self.state.allow_half_close || !self.io.read_buf().is_empty() {
498            return Poll::Pending;
499        }
500
501        let num_read = ready!(self.force_io_read(cx)).map_err(crate::Error::new_io)?;
502
503        if num_read == 0 {
504            trace!("found unexpected EOF on busy connection: {:?}", self.state);
505            self.state.close_read();
506            Poll::Ready(Err(crate::Error::new_incomplete()))
507        } else {
508            Poll::Ready(Ok(()))
509        }
510    }
511
512    fn force_io_read(&mut self, cx: &mut Context<'_>) -> Poll<io::Result<usize>> {
513        debug_assert!(!self.state.is_read_closed());
514
515        let result = ready!(self.io.poll_read_from_io(cx));
516        Poll::Ready(result.map_err(|e| {
517            trace!(error = %e, "force_io_read; io error");
518            self.state.close();
519            e
520        }))
521    }
522
523    fn maybe_notify(&mut self, cx: &mut Context<'_>) {
524        // its possible that we returned NotReady from poll() without having
525        // exhausted the underlying Io. We would have done this when we
526        // determined we couldn't keep reading until we knew how writing
527        // would finish.
528
529        match self.state.reading {
530            Reading::Continue(..) | Reading::Body(..) | Reading::KeepAlive | Reading::Closed => {
531                return
532            }
533            Reading::Init => (),
534        }
535
536        match self.state.writing {
537            Writing::Body(..) => return,
538            Writing::Init | Writing::KeepAlive | Writing::Closed => (),
539        }
540
541        if !self.io.is_read_blocked() {
542            if self.io.read_buf().is_empty() {
543                match self.io.poll_read_from_io(cx) {
544                    Poll::Ready(Ok(n)) => {
545                        if n == 0 {
546                            trace!("maybe_notify; read eof");
547                            if self.state.is_idle() {
548                                self.state.close();
549                            } else {
550                                self.close_read();
551                            }
552                            return;
553                        }
554                    }
555                    Poll::Pending => {
556                        trace!("maybe_notify; read_from_io blocked");
557                        return;
558                    }
559                    Poll::Ready(Err(e)) => {
560                        trace!("maybe_notify; read_from_io error: {}", e);
561                        self.state.close();
562                        self.state.error = Some(crate::Error::new_io(e));
563                    }
564                }
565            }
566            self.state.notify_read = true;
567        }
568    }
569
570    fn try_keep_alive(&mut self, cx: &mut Context<'_>) {
571        self.state.try_keep_alive::<T>();
572        self.maybe_notify(cx);
573    }
574
575    pub(crate) fn can_write_head(&self) -> bool {
576        if !T::should_read_first() && matches!(self.state.reading, Reading::Closed) {
577            return false;
578        }
579
580        match self.state.writing {
581            Writing::Init => self.io.can_headers_buf(),
582            _ => false,
583        }
584    }
585
586    pub(crate) fn can_write_body(&self) -> bool {
587        match self.state.writing {
588            Writing::Body(..) => true,
589            Writing::Init | Writing::KeepAlive | Writing::Closed => false,
590        }
591    }
592
593    pub(crate) fn can_buffer_body(&self) -> bool {
594        self.io.can_buffer()
595    }
596
597    /// Whether bytes are sitting in the write buffer waiting to be flushed.
598    pub(crate) fn has_buffered_write(&self) -> bool {
599        self.io.has_buffered_write()
600    }
601
602    pub(crate) fn write_head(&mut self, head: MessageHead<T::Outgoing>, body: Option<BodyLength>) {
603        if let Some(encoder) = self.encode_head(head, body) {
604            self.state.writing = if !encoder.is_eof() {
605                Writing::Body(encoder)
606            } else if encoder.is_last() {
607                Writing::Closed
608            } else {
609                Writing::KeepAlive
610            };
611        }
612    }
613
614    fn encode_head(
615        &mut self,
616        mut head: MessageHead<T::Outgoing>,
617        body: Option<BodyLength>,
618    ) -> Option<Encoder> {
619        debug_assert!(self.can_write_head());
620
621        if !T::should_read_first() {
622            self.state.busy();
623            // A client request carrying `Connection: close` must not be pooled or
624            // reused. hyper otherwise derives connection reuse from the response
625            // alone, so a backend that ignores the request-side close (omits
626            // `Connection: close` in its response) would leave the connection in
627            // the pool. Disable keep-alive up front so the connection is evicted
628            // regardless of the response.
629            if headers::connection_any_close(&head.headers) {
630                self.state.disable_keep_alive();
631            }
632        }
633
634        self.enforce_version(&mut head);
635
636        let buf = self.io.headers_buf();
637        match super::role::encode_headers::<T>(
638            Encode {
639                head: &mut head,
640                body,
641                #[cfg(feature = "server")]
642                keep_alive: self.state.wants_keep_alive(),
643                req_method: &mut self.state.method,
644                title_case_headers: self.state.title_case_headers,
645                #[cfg(feature = "server")]
646                date_header: self.state.date_header,
647            },
648            buf,
649        ) {
650            Ok(encoder) => {
651                debug_assert!(self.state.cached_headers.is_none());
652                debug_assert!(head.headers.is_empty());
653                self.state.cached_headers = Some(head.headers);
654
655                #[cfg(feature = "client")]
656                {
657                    self.state.on_informational =
658                        head.extensions.remove::<crate::ext::OnInformational>();
659                }
660
661                Some(encoder)
662            }
663            Err(err) => {
664                self.state.error = Some(err);
665                self.state.writing = Writing::Closed;
666                None
667            }
668        }
669    }
670
671    // Fix keep-alive when Connection: keep-alive header is not present
672    fn fix_keep_alive(&mut self, head: &mut MessageHead<T::Outgoing>) {
673        let connection_entry = head.headers.entry(CONNECTION);
674        let outgoing_is_keep_alive = match &connection_entry {
675            Entry::Occupied(entry) => entry.iter().any(headers::connection_keep_alive),
676            Entry::Vacant(_) => false,
677        };
678
679        if !outgoing_is_keep_alive {
680            match head.version {
681                // If response is version 1.0 and keep-alive is not present in the response,
682                // disable keep-alive so the server closes the connection
683                Version::HTTP_10 => self.state.disable_keep_alive(),
684                // If response is version 1.1 and keep-alive is wanted, add
685                // Connection: keep-alive header when not present
686                Version::HTTP_11 if self.state.wants_keep_alive() => match connection_entry {
687                    Entry::Occupied(mut entry) => {
688                        entry.append(HeaderValue::from_static("keep-alive"));
689                    }
690                    Entry::Vacant(entry) => {
691                        entry.insert(HeaderValue::from_static("keep-alive"));
692                    }
693                },
694                _ => (),
695            }
696        }
697    }
698
699    // If we know the remote speaks an older version, we try to fix up any messages
700    // to work with our older peer.
701    fn enforce_version(&mut self, head: &mut MessageHead<T::Outgoing>) {
702        match self.state.version {
703            Version::HTTP_10 => {
704                // Fixes response or connection when keep-alive header is not present
705                self.fix_keep_alive(head);
706                // If the remote only knows HTTP/1.0, we should force ourselves
707                // to do only speak HTTP/1.0 as well.
708                head.version = Version::HTTP_10;
709            }
710            Version::HTTP_11 => {
711                if let KA::Disabled = self.state.keep_alive.status() {
712                    match head.headers.entry(CONNECTION) {
713                        Entry::Occupied(mut entry) => {
714                            if !entry.iter().any(headers::connection_close) {
715                                entry.append(HeaderValue::from_static("close"));
716                            }
717                        }
718                        Entry::Vacant(entry) => {
719                            entry.insert(HeaderValue::from_static("close"));
720                        }
721                    }
722                }
723            }
724            _ => (),
725        }
726        // If the remote speaks HTTP/1.1, then it *should* be fine with
727        // both HTTP/1.0 and HTTP/1.1 from us. So again, we just let
728        // the user's headers be.
729    }
730
731    pub(crate) fn write_body(&mut self, chunk: B) {
732        debug_assert!(self.can_write_body() && self.can_buffer_body());
733        // empty chunks should be discarded at Dispatcher level
734        debug_assert!(chunk.remaining() != 0);
735
736        let state = match &mut self.state.writing {
737            Writing::Body(encoder) => {
738                self.io.buffer(encoder.encode(chunk));
739
740                if !encoder.is_eof() {
741                    return;
742                }
743
744                if encoder.is_last() {
745                    Writing::Closed
746                } else {
747                    Writing::KeepAlive
748                }
749            }
750            _ => unreachable!("write_body invalid state: {:?}", self.state.writing),
751        };
752
753        self.state.writing = state;
754    }
755
756    pub(crate) fn write_trailers(&mut self, trailers: HeaderMap) {
757        if T::is_server() && !self.state.allow_trailer_fields {
758            debug!("trailers not allowed to be sent");
759            return;
760        }
761        debug_assert!(self.can_write_body() && self.can_buffer_body());
762
763        match &mut self.state.writing {
764            Writing::Body(encoder) => {
765                if let Some(enc_buf) =
766                    encoder.encode_trailers(trailers, self.state.title_case_headers)
767                {
768                    self.io.buffer(enc_buf);
769
770                    self.state.writing = if encoder.is_last() || encoder.is_close_delimited() {
771                        Writing::Closed
772                    } else {
773                        Writing::KeepAlive
774                    };
775                }
776            }
777            _ => unreachable!("write_trailers invalid state: {:?}", self.state.writing),
778        }
779    }
780
781    pub(crate) fn write_body_and_end(&mut self, chunk: B) {
782        debug_assert!(self.can_write_body() && self.can_buffer_body());
783        // empty chunks should be discarded at Dispatcher level
784        debug_assert!(chunk.remaining() != 0);
785
786        let state = match &mut self.state.writing {
787            Writing::Body(encoder) => {
788                let can_keep_alive = encoder.encode_and_end(chunk, self.io.write_buf());
789                if can_keep_alive {
790                    Writing::KeepAlive
791                } else {
792                    Writing::Closed
793                }
794            }
795            _ => unreachable!("write_body invalid state: {:?}", self.state.writing),
796        };
797
798        self.state.writing = state;
799    }
800
801    pub(crate) fn end_body(&mut self) -> crate::Result<()> {
802        debug_assert!(self.can_write_body());
803
804        let encoder = match &mut self.state.writing {
805            Writing::Body(enc) => enc,
806            _ => return Ok(()),
807        };
808
809        // end of stream, that means we should try to eof
810        match encoder.end() {
811            Ok(end) => {
812                if let Some(end) = end {
813                    self.io.buffer(end);
814                }
815
816                self.state.writing = if encoder.is_last() || encoder.is_close_delimited() {
817                    Writing::Closed
818                } else {
819                    Writing::KeepAlive
820                };
821
822                Ok(())
823            }
824            Err(not_eof) => {
825                self.state.writing = Writing::Closed;
826                Err(crate::Error::new_body_write_aborted().with(not_eof))
827            }
828        }
829    }
830
831    // When we get a parse error, depending on what side we are, we might be able
832    // to write a response before closing the connection.
833    //
834    // - Client: there is nothing we can do
835    // - Server: if Response hasn't been written yet, we can send a 4xx response
836    fn on_parse_error(&mut self, err: crate::Error) -> crate::Result<()> {
837        if let Writing::Init = self.state.writing {
838            if self.has_h2_prefix() {
839                return Err(crate::Error::new_version_h2());
840            }
841            if let Some(msg) = T::on_error(&err) {
842                // Drop the cached headers so as to not trigger a debug
843                // assert in `write_head`...
844                self.state.cached_headers.take();
845                self.write_head(msg, None);
846                self.state.error = Some(err);
847                return Ok(());
848            }
849        }
850
851        // fallback is pass the error back up
852        Err(err)
853    }
854
855    pub(crate) fn poll_flush(&mut self, cx: &mut Context<'_>) -> Poll<io::Result<()>> {
856        ready!(Pin::new(&mut self.io).poll_flush(cx))?;
857        self.try_keep_alive(cx);
858        trace!("flushed({}): {:?}", T::LOG, self.state);
859        Poll::Ready(Ok(()))
860    }
861
862    pub(crate) fn poll_shutdown(&mut self, cx: &mut Context<'_>) -> Poll<io::Result<()>> {
863        match ready!(self.io.poll_shutdown(cx)) {
864            Ok(()) => {
865                trace!("shut down IO complete");
866                Poll::Ready(Ok(()))
867            }
868            Err(e) => {
869                debug!("error shutting down IO: {}", e);
870                Poll::Ready(Err(e))
871            }
872        }
873    }
874
875    /// If the read side can be cheaply drained, do so. Otherwise, close.
876    pub(super) fn poll_drain_or_close_read(&mut self, cx: &mut Context<'_>) {
877        if let Reading::Continue(decoder) = &mut self.state.reading {
878            // skip sending the 100-continue
879            // just move forward to a read, in case a tiny body was included
880            self.state.reading = Reading::Body(decoder.clone());
881        }
882
883        let _ = self.poll_read_body(cx);
884
885        // If still in Reading::Body, just give up
886        match self.state.reading {
887            Reading::Init | Reading::KeepAlive => {
888                trace!("body drained")
889            }
890            _ => self.close_read(),
891        }
892    }
893
894    pub(crate) fn close_read(&mut self) {
895        self.state.close_read();
896    }
897
898    pub(crate) fn close_write(&mut self) {
899        self.state.close_write();
900    }
901
902    #[cfg(feature = "server")]
903    pub(crate) fn disable_keep_alive(&mut self) {
904        if self.state.is_idle() {
905            trace!("disable_keep_alive; closing idle connection");
906            self.state.close();
907        } else {
908            trace!("disable_keep_alive; in-progress connection");
909            self.state.disable_keep_alive();
910        }
911    }
912
913    pub(crate) fn take_error(&mut self) -> crate::Result<()> {
914        if let Some(err) = self.state.error.take() {
915            Err(err)
916        } else {
917            Ok(())
918        }
919    }
920
921    pub(super) fn on_upgrade(&mut self) -> crate::upgrade::OnUpgrade {
922        trace!("{}: prepare possible HTTP upgrade", T::LOG);
923        self.state.prepare_upgrade()
924    }
925}
926
927impl<I, B: Buf, T> fmt::Debug for Conn<I, B, T> {
928    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
929        f.debug_struct("Conn")
930            .field("state", &self.state)
931            .field("io", &self.io)
932            .finish()
933    }
934}
935
936// B and T are never pinned
937impl<I: Unpin, B, T> Unpin for Conn<I, B, T> {}
938
939struct State {
940    allow_half_close: bool,
941    /// Re-usable `HeaderMap` to reduce allocating new ones.
942    cached_headers: Option<HeaderMap>,
943    /// If an error occurs when there wasn't a direct way to return it
944    /// back to the user, this is set.
945    error: Option<crate::Error>,
946    /// Current keep-alive status.
947    keep_alive: KA,
948    /// If mid-message, the HTTP Method that started it.
949    ///
950    /// This is used to know things such as if the message can include
951    /// a body or not.
952    method: Option<Method>,
953    h1_parser_config: ParserConfig,
954    h1_max_headers: Option<usize>,
955    h1_max_header_size: Option<usize>,
956    #[cfg(feature = "server")]
957    h1_header_read_timeout: Option<Duration>,
958    #[cfg(feature = "server")]
959    h1_header_read_timeout_fut: Option<Pin<Box<dyn Sleep>>>,
960    #[cfg(feature = "server")]
961    h1_header_read_timeout_running: bool,
962    #[cfg(feature = "server")]
963    date_header: bool,
964    #[cfg(feature = "server")]
965    timer: Time,
966    preserve_header_case: bool,
967    #[cfg(feature = "ffi")]
968    preserve_header_order: bool,
969    title_case_headers: bool,
970    h09_responses: bool,
971    /// If set, called with each 1xx informational response received for
972    /// the current request. MUST be unset after a non-1xx response is
973    /// received.
974    #[cfg(feature = "client")]
975    on_informational: Option<crate::ext::OnInformational>,
976    /// Set to true when the Dispatcher should poll read operations
977    /// again. See the `maybe_notify` method for more.
978    notify_read: bool,
979    /// State of allowed reads.
980    reading: Reading,
981    /// State of allowed writes.
982    writing: Writing,
983    /// An expected pending HTTP upgrade.
984    upgrade: Option<crate::upgrade::Pending>,
985    /// Either HTTP/1.0 or 1.1 connection.
986    version: Version,
987    /// Flag to track if trailer fields are allowed to be sent.
988    allow_trailer_fields: bool,
989}
990
991#[derive(Debug)]
992enum Reading {
993    Init,
994    Continue(Decoder),
995    Body(Decoder),
996    KeepAlive,
997    Closed,
998}
999
1000enum Writing {
1001    Init,
1002    Body(Encoder),
1003    KeepAlive,
1004    Closed,
1005}
1006
1007impl fmt::Debug for State {
1008    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
1009        let mut builder = f.debug_struct("State");
1010        builder
1011            .field("reading", &self.reading)
1012            .field("writing", &self.writing)
1013            .field("keep_alive", &self.keep_alive);
1014
1015        // Only show error field if it's interesting...
1016        if let Some(error) = &self.error {
1017            builder.field("error", error);
1018        }
1019
1020        if self.allow_half_close {
1021            builder.field("allow_half_close", &true);
1022        }
1023
1024        // Purposefully leaving off other fields..
1025
1026        builder.finish_non_exhaustive()
1027    }
1028}
1029
1030impl fmt::Debug for Writing {
1031    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
1032        match self {
1033            Writing::Init => f.write_str("Init"),
1034            Writing::Body(enc) => f.debug_tuple("Body").field(enc).finish(),
1035            Writing::KeepAlive => f.write_str("KeepAlive"),
1036            Writing::Closed => f.write_str("Closed"),
1037        }
1038    }
1039}
1040
1041impl std::ops::BitAndAssign<bool> for KA {
1042    fn bitand_assign(&mut self, enabled: bool) {
1043        if !enabled {
1044            trace!("remote disabling keep-alive");
1045            *self = KA::Disabled;
1046        }
1047    }
1048}
1049
1050#[derive(Clone, Copy, Debug, Default)]
1051enum KA {
1052    Idle,
1053    #[default]
1054    Busy,
1055    Disabled,
1056}
1057
1058impl KA {
1059    fn idle(&mut self) {
1060        *self = KA::Idle;
1061    }
1062
1063    fn busy(&mut self) {
1064        *self = KA::Busy;
1065    }
1066
1067    fn disable(&mut self) {
1068        *self = KA::Disabled;
1069    }
1070
1071    fn status(&self) -> KA {
1072        *self
1073    }
1074}
1075
1076impl State {
1077    fn close(&mut self) {
1078        trace!("State::close()");
1079        self.reading = Reading::Closed;
1080        self.writing = Writing::Closed;
1081        self.keep_alive.disable();
1082    }
1083
1084    fn close_read(&mut self) {
1085        trace!("State::close_read()");
1086        self.reading = Reading::Closed;
1087        self.keep_alive.disable();
1088    }
1089
1090    fn close_write(&mut self) {
1091        trace!("State::close_write()");
1092        self.writing = Writing::Closed;
1093        self.keep_alive.disable();
1094    }
1095
1096    fn wants_keep_alive(&self) -> bool {
1097        !matches!(self.keep_alive.status(), KA::Disabled)
1098    }
1099
1100    fn try_keep_alive<T: Http1Transaction>(&mut self) {
1101        match (&self.reading, &self.writing) {
1102            (&Reading::KeepAlive, &Writing::KeepAlive) => {
1103                if let KA::Busy = self.keep_alive.status() {
1104                    self.idle::<T>();
1105                } else {
1106                    trace!(
1107                        "try_keep_alive({}): could keep-alive, but status = {:?}",
1108                        T::LOG,
1109                        self.keep_alive
1110                    );
1111                    self.close();
1112                }
1113            }
1114            (&Reading::Closed, &Writing::KeepAlive) | (&Reading::KeepAlive, &Writing::Closed) => {
1115                self.close();
1116            }
1117            _ => (),
1118        }
1119    }
1120
1121    fn disable_keep_alive(&mut self) {
1122        self.keep_alive.disable();
1123    }
1124
1125    fn busy(&mut self) {
1126        if let KA::Disabled = self.keep_alive.status() {
1127            return;
1128        }
1129        self.keep_alive.busy();
1130    }
1131
1132    fn idle<T: Http1Transaction>(&mut self) {
1133        debug_assert!(!self.is_idle(), "State::idle() called while idle");
1134
1135        self.method = None;
1136        self.keep_alive.idle();
1137
1138        if !self.is_idle() {
1139            self.close();
1140            return;
1141        }
1142
1143        self.reading = Reading::Init;
1144        self.writing = Writing::Init;
1145
1146        // !T::should_read_first() means Client.
1147        //
1148        // If Client connection has just gone idle, the Dispatcher
1149        // should try the poll loop one more time, so as to poll the
1150        // pending requests stream.
1151        if !T::should_read_first() {
1152            self.notify_read = true;
1153        }
1154
1155        #[cfg(feature = "server")]
1156        if self.h1_header_read_timeout.is_some() {
1157            // Next read will start and poll the header read timeout,
1158            // so we can close the connection if another header isn't
1159            // received in a timely manner.
1160            self.notify_read = true;
1161        }
1162    }
1163
1164    fn is_idle(&self) -> bool {
1165        matches!(self.keep_alive.status(), KA::Idle)
1166    }
1167
1168    fn is_read_closed(&self) -> bool {
1169        matches!(self.reading, Reading::Closed)
1170    }
1171
1172    fn is_write_closed(&self) -> bool {
1173        matches!(self.writing, Writing::Closed)
1174    }
1175
1176    fn prepare_upgrade(&mut self) -> crate::upgrade::OnUpgrade {
1177        let (tx, rx) = crate::upgrade::pending();
1178        self.upgrade = Some(tx);
1179        rx
1180    }
1181}
1182
1183#[cfg(test)]
1184mod tests {
1185    #[cfg(all(feature = "nightly", not(miri)))]
1186    #[bench]
1187    fn bench_read_head_short(b: &mut ::test::Bencher) {
1188        use super::*;
1189        use crate::common::io::Compat;
1190        let s = b"GET / HTTP/1.1\r\nHost: localhost:8080\r\n\r\n";
1191        let len = s.len();
1192        b.bytes = len as u64;
1193
1194        // an empty IO, we'll be skipping and using the read buffer anyways
1195        let io = Compat(tokio_test::io::Builder::new().build());
1196        let mut conn = Conn::<_, bytes::Bytes, crate::proto::h1::ServerTransaction>::new(io);
1197        *conn.io.read_buf_mut() = ::bytes::BytesMut::from(&s[..]);
1198        conn.state.cached_headers = Some(HeaderMap::with_capacity(2));
1199
1200        let rt = tokio::runtime::Builder::new_current_thread()
1201            .enable_all()
1202            .build()
1203            .unwrap();
1204
1205        b.iter(|| {
1206            rt.block_on(futures_util::future::poll_fn(|cx| {
1207                match conn.poll_read_head(cx) {
1208                    Poll::Ready(Some(Ok(x))) => {
1209                        ::test::black_box(&x);
1210                        let mut headers = x.0.headers;
1211                        headers.clear();
1212                        conn.state.cached_headers = Some(headers);
1213                    }
1214                    f => panic!("expected Ready(Some(Ok(..))): {:?}", f),
1215                }
1216
1217                conn.io.read_buf_mut().reserve(1);
1218                unsafe {
1219                    conn.io.read_buf_mut().set_len(len);
1220                }
1221                conn.state.reading = Reading::Init;
1222                Poll::Ready(())
1223            }));
1224        });
1225    }
1226
1227    // A client request carrying `Connection: close` must evict the connection
1228    // (disable keep-alive) at request-encode time, so it is never returned to the
1229    // pool for reuse — independent of whether the backend response echoes
1230    // `Connection: close`. hyper otherwise derives reuse from the response alone.
1231    #[cfg(feature = "client")]
1232    #[test]
1233    fn client_request_connection_close_disables_keep_alive() {
1234        use super::*;
1235        use crate::common::io::Compat;
1236        use crate::proto::RequestLine;
1237
1238        // Encodes a client GET (with the given Connection header lines, one
1239        // `append` each) on a fresh client Conn and returns whether the
1240        // connection remains reusable.
1241        fn remains_reusable_after_get(connection_values: &[&'static str]) -> bool {
1242            let io = Compat(tokio_test::io::Builder::new().build());
1243            let mut conn = Conn::<_, bytes::Bytes, crate::proto::h1::ClientTransaction>::new(io);
1244            assert!(
1245                conn.state.wants_keep_alive(),
1246                "a fresh client connection should want keep-alive"
1247            );
1248
1249            let mut headers = HeaderMap::new();
1250            for value in connection_values {
1251                headers.append(CONNECTION, HeaderValue::from_static(value));
1252            }
1253            let head = MessageHead {
1254                version: Version::HTTP_11,
1255                subject: RequestLine(Method::GET, "/".parse().unwrap()),
1256                headers,
1257                extensions: http::Extensions::new(),
1258            };
1259            conn.write_head(head, None);
1260            conn.state.wants_keep_alive()
1261        }
1262
1263        // Control: a request without `Connection: close` leaves the connection reusable.
1264        assert!(
1265            remains_reusable_after_get(&[]),
1266            "a keep-alive request must leave the connection reusable"
1267        );
1268        // Fix: a `Connection: close` request must disable keep-alive so the
1269        // connection is evicted regardless of the response.
1270        assert!(
1271            !remains_reusable_after_get(&["close"]),
1272            "a `Connection: close` request must disable keep-alive (connection evicted)"
1273        );
1274        // A `close` token in a comma-separated value is honored.
1275        assert!(
1276            !remains_reusable_after_get(&["keep-alive, close"]),
1277            "a `close` token in a comma-separated Connection value must disable keep-alive"
1278        );
1279        // A `close` in ANY of multiple Connection header lines is honored
1280        // (get_all, not just the first line).
1281        assert!(
1282            !remains_reusable_after_get(&["keep-alive", "close"]),
1283            "a `close` in any Connection header line must disable keep-alive"
1284        );
1285    }
1286
1287    use super::*;
1288    use crate::common::io::Compat;
1289    #[cfg(feature = "client")]
1290    use crate::proto::h1::ClientTransaction;
1291    #[cfg(feature = "server")]
1292    use crate::proto::h1::ServerTransaction;
1293    #[cfg(feature = "server")]
1294    use crate::proto::RequestLine;
1295    use bytes::Bytes;
1296
1297    fn poll_head<I, T>(
1298        conn: &mut Conn<Compat<I>, Bytes, T>,
1299    ) -> Poll<Option<crate::Result<(MessageHead<T::Incoming>, DecodedLength, Wants)>>>
1300    where
1301        I: tokio::io::AsyncRead + tokio::io::AsyncWrite + Unpin,
1302        T: Http1Transaction + Unpin,
1303    {
1304        tokio_test::task::spawn(()).enter(|cx, _| conn.poll_read_head(cx))
1305    }
1306
1307    fn ready<T>(poll: Poll<T>) -> T {
1308        match poll {
1309            Poll::Ready(value) => value,
1310            Poll::Pending => panic!("expected ready"),
1311        }
1312    }
1313
1314    #[cfg(feature = "server")]
1315    #[test]
1316    fn conn_reads_request_head() {
1317        let io = tokio_test::io::Builder::new()
1318            .read(b"GET / HTTP/1.1\r\n\r\n")
1319            .build();
1320        let mut conn = Conn::<_, Bytes, ServerTransaction>::new(Compat::new(io));
1321
1322        let (head, body, _) = ready(poll_head(&mut conn))
1323            .expect("message")
1324            .expect("valid request");
1325        assert_eq!(head.subject, RequestLine(Method::GET, "/".parse().unwrap()));
1326        assert_eq!(body, DecodedLength::ZERO);
1327    }
1328
1329    #[cfg(feature = "server")]
1330    #[test]
1331    fn conn_reads_partial_request_head() {
1332        tokio_test::task::spawn(()).enter(|cx, _| {
1333            let (io, mut handle) = tokio_test::io::Builder::new().build_with_handle();
1334            let mut conn = Conn::<_, Bytes, ServerTransaction>::new(Compat::new(io));
1335            handle.read(b"GET / HTTP");
1336            assert!(conn.poll_read_head(cx).is_pending());
1337            handle.read(b"/1.1\r\nHost: foo.bar\r\n\r\n");
1338            assert!(conn.poll_read_head(cx).is_ready());
1339        });
1340    }
1341
1342    #[cfg(feature = "server")]
1343    #[test]
1344    fn conn_accepts_eof_when_idle() {
1345        let io = tokio_test::io::Builder::new().build();
1346        let mut conn = Conn::<_, Bytes, ServerTransaction>::new(Compat::new(io));
1347        conn.state.idle::<ServerTransaction>();
1348        assert!(matches!(poll_head(&mut conn), Poll::Ready(None)));
1349    }
1350
1351    #[cfg(feature = "server")]
1352    #[test]
1353    fn conn_rejects_eof_during_partial_head() {
1354        let io = tokio_test::io::Builder::new()
1355            .read(b"GET / HTTP/1.1")
1356            .build();
1357        let mut conn = Conn::<_, Bytes, ServerTransaction>::new(Compat::new(io));
1358        conn.state.idle::<ServerTransaction>();
1359        let err = ready(poll_head(&mut conn))
1360            .expect("error result")
1361            .expect_err("partial head must fail");
1362        assert!(err.is_incomplete_message(), "unexpected error: {err:?}");
1363    }
1364
1365    #[cfg(feature = "client")]
1366    #[test]
1367    fn client_rejects_eof_while_busy() {
1368        let io = tokio_test::io::Builder::new().build();
1369        let mut client = Conn::<_, Bytes, ClientTransaction>::new(Compat::new(io));
1370        client.state.busy();
1371        client.state.writing = Writing::KeepAlive;
1372        let err = ready(poll_head(&mut client))
1373            .expect("error result")
1374            .expect_err("client EOF must fail");
1375        assert!(err.is_incomplete_message(), "unexpected error: {err:?}");
1376    }
1377
1378    #[cfg(feature = "server")]
1379    #[test]
1380    fn server_accepts_eof_while_busy() {
1381        let io = tokio_test::io::Builder::new().build();
1382        let mut server = Conn::<_, Bytes, ServerTransaction>::new(Compat::new(io));
1383        server.state.busy();
1384        assert!(matches!(poll_head(&mut server), Poll::Ready(None)));
1385    }
1386
1387    #[cfg(feature = "client")]
1388    #[test]
1389    fn conn_reads_empty_response_before_eof() {
1390        let io = tokio_test::io::Builder::new()
1391            .read(b"HTTP/1.1 200 OK\r\nContent-Length: 0\r\n\r\n")
1392            .build();
1393        let mut conn = Conn::<_, Bytes, ClientTransaction>::new(Compat::new(io));
1394        conn.state.busy();
1395        conn.state.writing = Writing::KeepAlive;
1396        let (_, body, _) = ready(poll_head(&mut conn))
1397            .expect("response")
1398            .expect("valid response");
1399        assert_eq!(body, DecodedLength::ZERO);
1400    }
1401
1402    #[cfg(feature = "server")]
1403    #[test]
1404    fn conn_reads_body_and_reports_end() {
1405        let io = tokio_test::io::Builder::new()
1406            .read(b"POST / HTTP/1.1\r\nContent-Length: 5\r\n\r\n12345")
1407            .wait(std::time::Duration::from_secs(1))
1408            .build();
1409        let mut conn = Conn::<_, Bytes, ServerTransaction>::new(Compat::new(io));
1410        let (_, body, _) = ready(poll_head(&mut conn))
1411            .expect("request")
1412            .expect("valid request");
1413        assert_eq!(body, DecodedLength::new(5));
1414
1415        tokio_test::task::spawn(()).enter(|cx, _| {
1416            let frame = conn.poll_read_body(cx);
1417            let data = ready(frame)
1418                .expect("body frame")
1419                .expect("valid body")
1420                .into_data()
1421                .expect("data frame");
1422            assert_eq!(data, "12345");
1423            assert!(
1424                !conn.can_read_body(),
1425                "the complete body must return to head-reading state"
1426            );
1427        });
1428    }
1429
1430    #[cfg(feature = "server")]
1431    #[test]
1432    fn closed_conn_cannot_read_or_write() {
1433        let io = tokio_test::io::Builder::new().build();
1434        let mut conn = Conn::<_, Bytes, ServerTransaction>::new(Compat::new(io));
1435        conn.state.close();
1436        assert!(conn.is_read_closed());
1437        assert!(conn.is_write_closed());
1438        assert!(!conn.can_read_head());
1439        assert!(!conn.can_write_head());
1440    }
1441
1442    #[cfg(feature = "server")]
1443    #[test]
1444    fn conn_writes_chunked_body() {
1445        let io = tokio_test::io::Builder::new()
1446            .write(b"7\r\nheaders\r\n0\r\n\r\n")
1447            .build();
1448        let mut conn = Conn::<_, Bytes, ServerTransaction>::new(Compat::new(io));
1449        conn.state.writing = Writing::Body(Encoder::chunked());
1450        conn.write_body(Bytes::from_static(b"headers"));
1451        conn.end_body().unwrap();
1452        tokio_test::task::spawn(()).enter(|cx, _| {
1453            assert!(conn.poll_flush(cx).is_ready());
1454        });
1455    }
1456}