private.h: rename to contain dir
[platform/upstream/libwebsockets.git] / lib / roles / http / private-lib-roles-http.h
1 /*
2  * libwebsockets - small server side websockets and web server implementation
3  *
4  * Copyright (C) 2010 - 2018 Andy Green <andy@warmcat.com>
5  *
6  *  This library is free software; you can redistribute it and/or
7  *  modify it under the terms of the GNU Lesser General Public
8  *  License as published by the Free Software Foundation:
9  *  version 2.1 of the License.
10  *
11  *  This library is distributed in the hope that it will be useful,
12  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
13  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
14  *  Lesser General Public License for more details.
15  *
16  *  You should have received a copy of the GNU Lesser General Public
17  *  License along with this library; if not, write to the Free Software
18  *  Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
19  *  MA  02110-1301  USA
20  *
21  *  This is included from private-lib-core.h if either H1 or H2 roles are
22  *  enabled
23  */
24
25 #if defined(LWS_WITH_HUBBUB)
26   #include <hubbub/hubbub.h>
27   #include <hubbub/parser.h>
28  #endif
29
30 #if defined(LWS_WITH_HTTP_STREAM_COMPRESSION)
31 #include "private-lib-roles-http-compression.h"
32 #endif
33
34 #define lwsi_role_http(wsi) (lwsi_role_h1(wsi) || lwsi_role_h2(wsi))
35
36 enum http_version {
37         HTTP_VERSION_1_0,
38         HTTP_VERSION_1_1,
39         HTTP_VERSION_2
40 };
41
42 enum http_conn_type {
43         HTTP_CONNECTION_CLOSE,
44         HTTP_CONNECTION_KEEP_ALIVE
45 };
46
47 /*
48  * This is totally opaque to code using the library.  It's exported as a
49  * forward-reference pointer-only declaration; the user can use the pointer with
50  * other APIs to get information out of it.
51  */
52
53 #if defined(LWS_WITH_ESP32)
54 typedef uint16_t ah_data_idx_t;
55 #else
56 typedef uint32_t ah_data_idx_t;
57 #endif
58
59 struct lws_fragments {
60         ah_data_idx_t   offset;
61         uint16_t        len;
62         uint8_t         nfrag; /* which ah->frag[] continues this content, or 0 */
63         uint8_t         flags; /* only http2 cares */
64 };
65
66 #if defined(LWS_WITH_RANGES)
67 enum range_states {
68         LWSRS_NO_ACTIVE_RANGE,
69         LWSRS_BYTES_EQ,
70         LWSRS_FIRST,
71         LWSRS_STARTING,
72         LWSRS_ENDING,
73         LWSRS_COMPLETED,
74         LWSRS_SYNTAX,
75 };
76
77 struct lws_range_parsing {
78         unsigned long long start, end, extent, agg, budget;
79         const char buf[128];
80         int pos;
81         enum range_states state;
82         char start_valid, end_valid, ctr, count_ranges, did_try, inside, send_ctr;
83 };
84
85 int
86 lws_ranges_init(struct lws *wsi, struct lws_range_parsing *rp,
87                 unsigned long long extent);
88 int
89 lws_ranges_next(struct lws_range_parsing *rp);
90 void
91 lws_ranges_reset(struct lws_range_parsing *rp);
92 #endif
93
94 /*
95  * these are assigned from a pool held in the context.
96  * Both client and server mode uses them for http header analysis
97  */
98
99 struct allocated_headers {
100         struct allocated_headers *next; /* linked list */
101         struct lws *wsi; /* owner */
102         char *data; /* prepared by context init to point to dedicated storage */
103         ah_data_idx_t data_length;
104         /*
105          * the randomly ordered fragments, indexed by frag_index and
106          * lws_fragments->nfrag for continuation.
107          */
108         struct lws_fragments frags[WSI_TOKEN_COUNT];
109         time_t assigned;
110         /*
111          * for each recognized token, frag_index says which frag[] his data
112          * starts in (0 means the token did not appear)
113          * the actual header data gets dumped as it comes in, into data[]
114          */
115         uint8_t frag_index[WSI_TOKEN_COUNT];
116
117 #ifndef LWS_NO_CLIENT
118         char initial_handshake_hash_base64[30];
119 #endif
120         int hdr_token_idx;
121
122         ah_data_idx_t pos;
123         ah_data_idx_t http_response;
124         ah_data_idx_t current_token_limit;
125
126 #if defined(LWS_WITH_CUSTOM_HEADERS)
127         ah_data_idx_t unk_pos; /* to undo speculative unknown header */
128         ah_data_idx_t unk_value_pos;
129
130         ah_data_idx_t unk_ll_head;
131         ah_data_idx_t unk_ll_tail;
132 #endif
133
134         int16_t lextable_pos;
135
136         uint8_t in_use;
137         uint8_t nfrag;
138         char /*enum uri_path_states */ ups;
139         char /*enum uri_esc_states */ ues;
140
141         char esc_stash;
142         char post_literal_equal;
143         uint8_t /* enum lws_token_indexes */ parser_state;
144 };
145
146
147
148 #if defined(LWS_WITH_HUBBUB)
149 struct lws_rewrite {
150         hubbub_parser *parser;
151         hubbub_parser_optparams params;
152         const char *from, *to;
153         int from_len, to_len;
154         unsigned char *p, *end;
155         struct lws *wsi;
156 };
157 static LWS_INLINE int hstrcmp(hubbub_string *s, const char *p, int len)
158 {
159         if ((int)s->len != len)
160                 return 1;
161
162         return strncmp((const char *)s->ptr, p, len);
163 }
164 typedef hubbub_error (*hubbub_callback_t)(const hubbub_token *token, void *pw);
165 LWS_EXTERN struct lws_rewrite *
166 lws_rewrite_create(struct lws *wsi, hubbub_callback_t cb, const char *from, const char *to);
167 LWS_EXTERN void
168 lws_rewrite_destroy(struct lws_rewrite *r);
169 LWS_EXTERN int
170 lws_rewrite_parse(struct lws_rewrite *r, const unsigned char *in, int in_len);
171 #endif
172
173 struct lws_pt_role_http {
174         struct allocated_headers *ah_list;
175         struct lws *ah_wait_list;
176 #ifdef LWS_WITH_CGI
177         struct lws_cgi *cgi_list;
178 #endif
179         int ah_wait_list_length;
180         uint32_t ah_pool_length;
181
182         int ah_count_in_use;
183 };
184
185 struct lws_peer_role_http {
186         uint32_t count_ah;
187         uint32_t total_ah;
188 };
189
190 struct lws_vhost_role_http {
191         char http_proxy_address[128];
192         const struct lws_http_mount *mount_list;
193         const char *error_document_404;
194         unsigned int http_proxy_port;
195 };
196
197 #ifdef LWS_WITH_ACCESS_LOG
198 struct lws_access_log {
199         char *header_log;
200         char *user_agent;
201         char *referrer;
202         unsigned long sent;
203         int response;
204 };
205 #endif
206
207 #define LWS_HTTP_CHUNK_HDR_MAX_SIZE (6 + 2) /* 6 hex digits and then CRLF */
208 #define LWS_HTTP_CHUNK_TRL_MAX_SIZE (2 + 5) /* CRLF, then maybe 0 CRLF CRLF */
209
210 struct _lws_http_mode_related {
211         struct lws *new_wsi_list;
212
213         unsigned char *pending_return_headers;
214         size_t pending_return_headers_len;
215         size_t prh_content_length;
216
217 #if defined(LWS_WITH_HTTP_PROXY)
218         struct lws_rewrite *rw;
219         struct lws_buflist *buflist_post_body;
220 #endif
221         struct allocated_headers *ah;
222         struct lws *ah_wait_list;
223
224         lws_filepos_t filepos;
225         lws_filepos_t filelen;
226         lws_fop_fd_t fop_fd;
227
228 #if defined(LWS_WITH_RANGES)
229         struct lws_range_parsing range;
230         char multipart_content_type[64];
231 #endif
232
233 #ifdef LWS_WITH_ACCESS_LOG
234         struct lws_access_log access_log;
235 #endif
236 #ifdef LWS_WITH_CGI
237         struct lws_cgi *cgi; /* wsi being cgi master have one of these */
238 #endif
239 #if defined(LWS_WITH_HTTP_STREAM_COMPRESSION)
240         struct lws_compression_support *lcs;
241         lws_comp_ctx_t comp_ctx;
242         unsigned char comp_accept_mask;
243 #endif
244
245         enum http_version request_version;
246         enum http_conn_type conn_type;
247         lws_filepos_t tx_content_length;
248         lws_filepos_t tx_content_remain;
249         lws_filepos_t rx_content_length;
250         lws_filepos_t rx_content_remain;
251
252 #if defined(LWS_WITH_HTTP_PROXY)
253         unsigned int perform_rewrite:1;
254         unsigned int proxy_clientside:1;
255         unsigned int proxy_parent_chunked:1;
256 #endif
257         unsigned int deferred_transaction_completed:1;
258         unsigned int content_length_explicitly_zero:1;
259         unsigned int did_stream_close:1;
260 };
261
262
263 #ifndef LWS_NO_CLIENT
264 enum lws_chunk_parser {
265         ELCP_HEX,
266         ELCP_CR,
267         ELCP_CONTENT,
268         ELCP_POST_CR,
269         ELCP_POST_LF,
270 };
271 #endif
272
273 enum lws_parse_urldecode_results {
274         LPUR_CONTINUE,
275         LPUR_SWALLOW,
276         LPUR_FORBID,
277         LPUR_EXCESSIVE,
278 };
279
280 enum lws_check_basic_auth_results {
281         LCBA_CONTINUE,
282         LCBA_FAILED_AUTH,
283         LCBA_END_TRANSACTION,
284 };
285
286 enum lws_check_basic_auth_results
287 lws_check_basic_auth(struct lws *wsi, const char *basic_auth_login_file);
288
289 int
290 lws_unauthorised_basic_auth(struct lws *wsi);
291
292 int
293 lws_read_h1(struct lws *wsi, unsigned char *buf, lws_filepos_t len);
294
295 void
296 _lws_header_table_reset(struct allocated_headers *ah);
297
298 LWS_EXTERN int
299 _lws_destroy_ah(struct lws_context_per_thread *pt, struct allocated_headers *ah);
300
301 int
302 lws_http_proxy_start(struct lws *wsi, const struct lws_http_mount *hit,
303                      char *uri_ptr, char ws);
304
305 typedef struct lws_sorted_usec_list lws_sorted_usec_list_t;
306
307 void
308 lws_sul_http_ah_lifecheck(lws_sorted_usec_list_t *sul);