Line data Source code
1 : //
2 : // Copyright (c) 2021 Vinnie Falco (vinnie.falco@gmail.com)
3 : //
4 : // Distributed under the Boost Software License, Version 1.0. (See accompanying
5 : // file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
6 : //
7 : // Official repository: https://github.com/cppalliance/http_proto
8 : //
9 :
10 : #ifndef BOOST_HTTP_PROTO_METADATA_HPP
11 : #define BOOST_HTTP_PROTO_METADATA_HPP
12 :
13 : #include <boost/http_proto/detail/config.hpp>
14 : #include <boost/http_proto/error.hpp> // VFALCO TEMPORARY
15 : #include <boost/system/error_code.hpp>
16 : #include <cstdint>
17 : #include <cstdlib>
18 :
19 : namespace boost {
20 : namespace http_proto {
21 :
22 : //------------------------------------------------
23 :
24 : /** Identifies the payload type of a message
25 : */
26 : enum class payload
27 : {
28 : // VFALCO 3 space indent or
29 : // else Doxygen malfunctions
30 :
31 : /**
32 : * This message has no payload
33 : */
34 : none
35 :
36 : /**
37 : * The payload is unknown due to errors
38 : */
39 : ,error
40 :
41 : /**
42 : * This message has a known payload size
43 : */
44 : ,size
45 :
46 : /**
47 : * This message contains a chunked payload
48 : */
49 : ,chunked
50 :
51 : /**
52 : * The payload for this message continues until EOF
53 : */
54 : ,to_eof
55 : };
56 :
57 : /** The effective encoding of the body octets.
58 : */
59 : enum class
60 : encoding
61 : {
62 : /**
63 : * Indicates the body is not encoded.
64 : */
65 : identity,
66 :
67 : /**
68 : * Indicates the body has deflate applied.
69 : */
70 : deflate,
71 :
72 : /**
73 : * Indicates the body has gzip applied.
74 : */
75 : gzip
76 : };
77 :
78 : //------------------------------------------------
79 :
80 : /** Metadata about a request or response
81 : */
82 : struct metadata
83 : {
84 : /** Metadata for the Connection field
85 : */
86 : struct connection_t
87 : {
88 : /** Error status of Connection
89 : */
90 : system::error_code ec;
91 :
92 : /** The total number of fields
93 : */
94 : std::size_t count = 0;
95 :
96 : /** true if a close token is present
97 : */
98 : bool close = false;
99 :
100 : /** true if a keep-alive token is present
101 : */
102 : bool keep_alive = false;
103 :
104 : /** true if an upgrade token is present
105 : */
106 : bool upgrade = false;
107 :
108 : #ifdef BOOST_HTTP_PROTO_AGGREGATE_WORKAROUND
109 : constexpr
110 3416 : connection_t() = default;
111 :
112 : constexpr
113 15 : connection_t(
114 : system::error_code ec_,
115 : std::size_t count_,
116 : bool close_,
117 : bool keep_alive_,
118 : bool upgrade_) noexcept
119 15 : : ec(ec_)
120 15 : , count(count_)
121 15 : , close(close_)
122 15 : , keep_alive(keep_alive_)
123 15 : , upgrade(upgrade_)
124 : {
125 15 : }
126 : #endif
127 : };
128 :
129 : //--------------------------------------------
130 :
131 : /** Metadata for the Content-Length field
132 : */
133 : struct content_length_t
134 : {
135 : /** Error status of Content-Length
136 : */
137 : system::error_code ec;
138 :
139 : /** The total number of fields
140 : */
141 : std::size_t count = 0;
142 :
143 : /** The value as an integer
144 :
145 : This is only valid when ec does
146 : not hold a failure, and when
147 : count is greater than zero.
148 : */
149 : std::uint64_t value = 0;
150 :
151 : #ifdef BOOST_HTTP_PROTO_AGGREGATE_WORKAROUND
152 : constexpr
153 3408 : content_length_t() = default;
154 :
155 : constexpr
156 11 : content_length_t(
157 : system::error_code ec_,
158 : std::size_t count_,
159 : std::uint64_t value_) noexcept
160 11 : : ec(ec_)
161 11 : , count(count_)
162 11 : , value(value_)
163 : {
164 11 : }
165 : #endif
166 : };
167 :
168 : //--------------------------------------------
169 :
170 : /** Metadata for the Expect field
171 : */
172 : struct expect_t
173 : {
174 : /** Error status of Expect
175 : */
176 : system::error_code ec;
177 :
178 : /** The total number of fields
179 : */
180 : std::size_t count = 0;
181 :
182 : /** True if Expect is 100-continue
183 : */
184 : bool is_100_continue = false;
185 :
186 : #ifdef BOOST_HTTP_PROTO_AGGREGATE_WORKAROUND
187 : constexpr
188 3418 : expect_t() = default;
189 :
190 : constexpr
191 14 : expect_t(
192 : system::error_code ec_,
193 : std::size_t count_,
194 : bool is_100_continue_) noexcept
195 14 : : ec(ec_)
196 14 : , count(count_)
197 14 : , is_100_continue(is_100_continue_)
198 : {
199 14 : }
200 : #endif
201 : };
202 :
203 : //--------------------------------------------
204 :
205 : /** Metadata for the Transfer-Encoding field
206 : */
207 : struct transfer_encoding_t
208 : {
209 : /** Error status of Content-Length
210 : */
211 : system::error_code ec;
212 :
213 : /** The total number of fields
214 : */
215 : std::size_t count = 0;
216 :
217 : /** The total number of codings
218 : */
219 : std::size_t codings = 0;
220 :
221 : /** True if valid and chunked is specified last
222 : */
223 : bool is_chunked = false;
224 :
225 : /** The effective body encoding.
226 :
227 : This indicates the type of encoding detected on the body,
228 : if the fields contain a valid encoding. Otherwise it will have
229 : @ref encoding::identity if the header is invalid.
230 :
231 : Whether or not the message entity is also chunked is set
232 : in @ref metadata::is_chunked and not here.
233 : */
234 : http_proto::encoding encoding =
235 : http_proto::encoding::identity;
236 :
237 : #ifdef BOOST_HTTP_PROTO_AGGREGATE_WORKAROUND
238 : constexpr
239 3613 : transfer_encoding_t() = default;
240 :
241 : constexpr
242 20 : transfer_encoding_t(
243 : system::error_code ec_,
244 : std::size_t count_,
245 : std::size_t codings_,
246 : bool is_chunked_) noexcept
247 20 : : ec(ec_)
248 20 : , count(count_)
249 20 : , codings(codings_)
250 20 : , is_chunked(is_chunked_)
251 20 : , encoding(
252 : http_proto::encoding::identity)
253 : {
254 20 : }
255 : #endif
256 : };
257 :
258 : //--------------------------------------------
259 :
260 : /** Metadata for Upgrade field
261 : */
262 : struct upgrade_t
263 : {
264 : /** Error status of Upgrade
265 : */
266 : system::error_code ec;
267 :
268 : /** The total number of fields
269 : */
270 : std::size_t count = 0;
271 :
272 : /** True if websocket appears at least once
273 : */
274 : bool websocket = false;
275 :
276 : #ifdef BOOST_HTTP_PROTO_AGGREGATE_WORKAROUND
277 : constexpr
278 3409 : upgrade_t() = default;
279 :
280 : constexpr
281 15 : upgrade_t(
282 : system::error_code ec_,
283 : std::size_t count_,
284 : bool websocket_) noexcept
285 15 : : ec(ec_)
286 15 : , count(count_)
287 15 : , websocket(websocket_)
288 : {
289 15 : }
290 : #endif
291 : };
292 :
293 : //--------------------------------------------
294 :
295 : /** True if payload is manually specified
296 :
297 : This flag is used to allow the caller
298 : to resolve problems with non-compliant
299 : values for Content-Length.
300 : */
301 : bool payload_override = false;
302 :
303 : /** The type of payload
304 : */
305 : http_proto::payload payload =
306 : http_proto::payload::none;
307 :
308 : /** The size of the payload if known
309 :
310 : This is only valid when @ref payload
311 : equals @ref http_proto::payload::size.
312 : */
313 : std::uint64_t payload_size = 0;
314 :
315 : //--------------------------------------------
316 :
317 : // header metadata
318 :
319 : /** Metadata for the Connection field.
320 : */
321 : connection_t connection;
322 :
323 : /** Metadata for the Content-Length field.
324 : */
325 : content_length_t content_length;
326 :
327 : /** Metadata for the Expect field.
328 : */
329 : expect_t expect;
330 :
331 : /** Metadata for the Transfer-Encoding field.
332 : */
333 : transfer_encoding_t transfer_encoding;
334 :
335 : /** Metadata for the Upgrade field.
336 : */
337 : upgrade_t upgrade;
338 :
339 : //--------------------------------------------
340 :
341 : /** Constructor
342 : */
343 3404 : constexpr metadata() = default;
344 : };
345 :
346 : } // http_proto
347 : } // boost
348 :
349 : #endif
|