1pub mod header;
12mod io;
13
14use futures::future::Either;
15use header::{Data, GoAway, Header, Ping, StreamId, WindowUpdate};
16use std::{convert::TryInto, num::TryFromIntError};
17
18pub use io::FrameDecodeError;
19pub(crate) use io::Io;
20
21#[derive(Clone, Debug, PartialEq, Eq)]
23pub struct Frame<T> {
24 header: Header<T>,
25 body: Vec<u8>,
26}
27
28impl<T> Frame<T> {
29 pub fn new(header: Header<T>) -> Self {
30 Frame {
31 header,
32 body: Vec::new(),
33 }
34 }
35
36 pub fn header(&self) -> &Header<T> {
37 &self.header
38 }
39
40 pub fn header_mut(&mut self) -> &mut Header<T> {
41 &mut self.header
42 }
43
44 pub(crate) fn right<U>(self) -> Frame<Either<U, T>> {
46 Frame {
47 header: self.header.right(),
48 body: self.body,
49 }
50 }
51
52 pub(crate) fn left<U>(self) -> Frame<Either<T, U>> {
54 Frame {
55 header: self.header.left(),
56 body: self.body,
57 }
58 }
59}
60
61impl<A: header::private::Sealed> From<Frame<A>> for Frame<()> {
62 fn from(f: Frame<A>) -> Frame<()> {
63 Frame {
64 header: f.header.into(),
65 body: f.body,
66 }
67 }
68}
69
70impl Frame<()> {
71 pub(crate) fn into_data(self) -> Frame<Data> {
72 Frame {
73 header: self.header.into_data(),
74 body: self.body,
75 }
76 }
77
78 pub(crate) fn into_window_update(self) -> Frame<WindowUpdate> {
79 Frame {
80 header: self.header.into_window_update(),
81 body: self.body,
82 }
83 }
84
85 pub(crate) fn into_ping(self) -> Frame<Ping> {
86 Frame {
87 header: self.header.into_ping(),
88 body: self.body,
89 }
90 }
91}
92
93impl Frame<Data> {
94 pub fn data(id: StreamId, b: Vec<u8>) -> Result<Self, TryFromIntError> {
95 Ok(Frame {
96 header: Header::data(id, b.len().try_into()?),
97 body: b,
98 })
99 }
100
101 pub fn close_stream(id: StreamId, ack: bool) -> Self {
102 let mut header = Header::data(id, 0);
103 header.fin();
104 if ack {
105 header.ack()
106 }
107
108 Frame::new(header)
109 }
110
111 pub fn body(&self) -> &[u8] {
112 &self.body
113 }
114
115 pub fn body_len(&self) -> u32 {
116 self.body().len() as u32
119 }
120
121 pub fn into_body(self) -> Vec<u8> {
122 self.body
123 }
124}
125
126impl Frame<WindowUpdate> {
127 pub fn window_update(id: StreamId, credit: u32) -> Self {
128 Frame {
129 header: Header::window_update(id, credit),
130 body: Vec::new(),
131 }
132 }
133}
134
135impl Frame<GoAway> {
136 pub fn term() -> Self {
137 Frame {
138 header: Header::term(),
139 body: Vec::new(),
140 }
141 }
142
143 pub fn protocol_error() -> Self {
144 Frame {
145 header: Header::protocol_error(),
146 body: Vec::new(),
147 }
148 }
149
150 pub fn internal_error() -> Self {
151 Frame {
152 header: Header::internal_error(),
153 body: Vec::new(),
154 }
155 }
156}