diff options
author | Christian Grothoff <christian@grothoff.org> | 2017-07-18 11:43:25 +0200 |
---|---|---|
committer | Christian Grothoff <christian@grothoff.org> | 2017-07-18 11:43:25 +0200 |
commit | 66066283bd3733b168db454dd9297ba4262e407d (patch) | |
tree | 0a8d18c2aaf1280bf2889663b710aefdf27ea063 /src/include/microhttpd2.h | |
parent | 17a75e59233b8af60b4135f297a187fdad7929b2 (diff) | |
download | libmicrohttpd-66066283bd3733b168db454dd9297ba4262e407d.tar.gz libmicrohttpd-66066283bd3733b168db454dd9297ba4262e407d.zip |
propsing NG API for MHD
Diffstat (limited to 'src/include/microhttpd2.h')
-rw-r--r-- | src/include/microhttpd2.h | 1960 |
1 files changed, 1960 insertions, 0 deletions
diff --git a/src/include/microhttpd2.h b/src/include/microhttpd2.h new file mode 100644 index 00000000..e97d748b --- /dev/null +++ b/src/include/microhttpd2.h | |||
@@ -0,0 +1,1960 @@ | |||
1 | /* | ||
2 | This file is part of libmicrohttpd | ||
3 | Copyright (C) 2006-2017 Christian Grothoff (and other contributing authors) | ||
4 | |||
5 | This library is free software; you can redistribute it and/or | ||
6 | modify it under the terms of the GNU Lesser General Public | ||
7 | License as published by the Free Software Foundation; either | ||
8 | version 2.1 of the License, or (at your option) any later version. | ||
9 | |||
10 | This library is distributed in the hope that it will be useful, | ||
11 | but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
12 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | ||
13 | Lesser General Public License for more details. | ||
14 | |||
15 | You should have received a copy of the GNU Lesser General Public | ||
16 | License along with this library; if not, write to the Free Software | ||
17 | Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA | ||
18 | */ | ||
19 | |||
20 | /** | ||
21 | * Just includes the NEW definitions for the NG-API. | ||
22 | * Note that we do not indicate which of the OLD APIs | ||
23 | * simply need to be kept vs. deprecated. | ||
24 | * | ||
25 | * The goal is to provide a basis for discussion! | ||
26 | * None of this is implemented yet. | ||
27 | * | ||
28 | * Main goals: | ||
29 | * - simplify application callbacks by splitting header/upload/post | ||
30 | * functionality currently provided by calling the same | ||
31 | * MHD_AccessHandlerCallback 3+ times into separate callbacks. | ||
32 | * - avoid repeated scans for URL matches via the new | ||
33 | * struct MHD_RequestHandlerCallbacks construction | ||
34 | * - provide default logarithmic implementation of URL scan | ||
35 | * => reduce strcmp(url) from >= 3n operations to "log n" | ||
36 | * per request. | ||
37 | * - better types, in particular avoid varargs for options | ||
38 | * - make it harder to pass inconsistent options | ||
39 | * - combine options and flags into more uniform API (at least | ||
40 | * exterally!) | ||
41 | * - simplify API use by using sane defaults (benefiting from | ||
42 | * breaking backwards compatibility) and making all options | ||
43 | * really optional, and where applicable avoid having options | ||
44 | * where the default works if nothing is specified | ||
45 | * - simplify API by moving rarely used http_version into | ||
46 | * MHD_request_get_information() | ||
47 | * - avoid 'int' for MHD_YES/MHD_NO by introducing `enum MHD_Bool` | ||
48 | * - improve terminology by eliminating confusion between | ||
49 | * 'request' and 'connection' | ||
50 | * - prepare API for having multiple TLS backends | ||
51 | * - use more consistent prefixes for related functions | ||
52 | * by using MHD_subject_verb_object naming convention, also | ||
53 | * at the same time avoid symbol conflict with legacy names | ||
54 | * (so we can have one binary implementing old and new | ||
55 | * library API at the same time via compatibility layer). | ||
56 | */ | ||
57 | |||
58 | |||
59 | /** | ||
60 | * Representation of 'bool' in the public API as stdbool.h may not | ||
61 | * always be available. | ||
62 | */ | ||
63 | enum MHD_Bool | ||
64 | { | ||
65 | |||
66 | /** | ||
67 | * MHD-internal return code for "NO". | ||
68 | */ | ||
69 | MHD_NO = 0, | ||
70 | |||
71 | /** | ||
72 | * MHD-internal return code for "YES". | ||
73 | */ | ||
74 | MHD_YES = 1 | ||
75 | }; | ||
76 | |||
77 | |||
78 | /** | ||
79 | * @brief Handle for a connection / HTTP request. | ||
80 | * | ||
81 | * With HTTP/1.1, multiple requests can be run over the same | ||
82 | * connection. However, MHD will only show one request per TCP | ||
83 | * connection to the client at any given time. | ||
84 | * | ||
85 | * Replaces `struct MHD_Connection`, renamed to better reflect | ||
86 | * what this object truly represents to the application using | ||
87 | * MHD. | ||
88 | * | ||
89 | * @ingroup request | ||
90 | */ | ||
91 | struct MHD_Request; | ||
92 | |||
93 | |||
94 | /** | ||
95 | * Enumeration used to define options in | ||
96 | * `struct MHD_Option`. Opaque to the application. | ||
97 | */ | ||
98 | enum MHD_OptionValue; | ||
99 | |||
100 | |||
101 | /** | ||
102 | * Option configuring the service. | ||
103 | */ | ||
104 | struct MHD_Option | ||
105 | { | ||
106 | /** | ||
107 | * Which option is being given. #MHD_OPTION_VALUE_END | ||
108 | * terminates the array. | ||
109 | */ | ||
110 | enum MHD_OptionValue option; | ||
111 | |||
112 | /** | ||
113 | * Option value. | ||
114 | */ | ||
115 | intptr_t value1; | ||
116 | |||
117 | /** | ||
118 | * Option value. | ||
119 | */ | ||
120 | intptr_t value2; | ||
121 | |||
122 | /** | ||
123 | * Option value. | ||
124 | */ | ||
125 | intptr_t value3; | ||
126 | |||
127 | }; | ||
128 | |||
129 | |||
130 | /** | ||
131 | * Returns terminating element of an option array. | ||
132 | * | ||
133 | * @return MHD option array terminator | ||
134 | */ | ||
135 | _MHD_EXTERN struct MHD_Option | ||
136 | MHD_option_end (void); | ||
137 | |||
138 | |||
139 | /** | ||
140 | * Set logging method. Specify NULL to disable logging entirely. By | ||
141 | * default (if this option is not given), we log error messages to | ||
142 | * stderr. | ||
143 | * | ||
144 | * @return MHD option | ||
145 | */ | ||
146 | _MHD_EXTERN struct MHD_Option | ||
147 | MHD_option_log (MHD_LogCallback logger, | ||
148 | void *cls logger_cls); | ||
149 | |||
150 | |||
151 | /** | ||
152 | * Convenience macro used to disable logging. | ||
153 | * | ||
154 | * @return MHD option that disables logging | ||
155 | */ | ||
156 | #define MHD_option_disable_logging() MHD_option_log (NULL, NULL) | ||
157 | |||
158 | |||
159 | /** | ||
160 | * Suppress use of "Date" header as this system has no RTC. | ||
161 | * | ||
162 | * @return MHD option | ||
163 | */ | ||
164 | _MHD_EXTERN struct MHD_Option | ||
165 | MHD_option_suppress_date_no_clock (void); | ||
166 | |||
167 | |||
168 | /** | ||
169 | * Use inter-thread communication channel. #MHD_option_enable_itc() | ||
170 | * can be used with #MHD_option_thread_internal() and is ignored with | ||
171 | * any "external" mode. It's required for use of | ||
172 | * #MHD_daemon_quiesce() or #MHD_connection_add(). This option is | ||
173 | * enforced by #MHD_option_allow_suspend_resume() and if there is no | ||
174 | * listen socket. #MHD_option_enable_itc() is always used | ||
175 | * automatically on platforms where select()/poll()/other ignore | ||
176 | * shutdown of listen socket. | ||
177 | * | ||
178 | * @return MHD option | ||
179 | */ | ||
180 | _MHD_EXTERN struct MHD_Option | ||
181 | MHD_option_enable_itc (void); | ||
182 | |||
183 | |||
184 | /** | ||
185 | * Enable `turbo`. Disables certain calls to `shutdown()`, | ||
186 | * enables aggressive non-blocking optimistic reads and | ||
187 | * other potentially unsafe optimizations. | ||
188 | * Most effects only happen with #MHD_ELS_EPOLL. | ||
189 | * | ||
190 | * @return MHD option | ||
191 | */ | ||
192 | _MHD_EXTERN struct MHD_Option | ||
193 | MHD_option_enable_turbo (void); | ||
194 | |||
195 | |||
196 | /** | ||
197 | * Enable suspend/resume functions, which also implies setting up | ||
198 | * #MHD_option_enable_itc() to signal resume. | ||
199 | * | ||
200 | * @return MHD option | ||
201 | */ | ||
202 | _MHD_EXTERN struct MHD_Option | ||
203 | MHD_option_allow_suspend_resume (void); | ||
204 | |||
205 | |||
206 | /** | ||
207 | * You need to set this option if you want to use HTTP "Upgrade". | ||
208 | * "Upgrade" may require usage of additional internal resources, | ||
209 | * which we do not want to use unless necessary. | ||
210 | * | ||
211 | * @return MHD option | ||
212 | */ | ||
213 | _MHD_EXTERN struct MHD_Option | ||
214 | MHD_option_allow_upgrade (void); | ||
215 | |||
216 | |||
217 | /** | ||
218 | * Possible levels of enforcement for TCP_FASTOPEN. | ||
219 | */ | ||
220 | enum MHD_FastOpenMethod | ||
221 | { | ||
222 | /** | ||
223 | * Disable use of TCP_FASTOPEN. | ||
224 | */ | ||
225 | MHD_FOM_DISABLE = -1, | ||
226 | |||
227 | /** | ||
228 | * Enable TCP_FASTOPEN where supported (Linux with a kernel >= 3.6). | ||
229 | * This is the default. | ||
230 | */ | ||
231 | MHD_FOM_AUTO = 0, | ||
232 | |||
233 | /** | ||
234 | * If TCP_FASTOPEN is not available, cause #MHD_daemon_start() to | ||
235 | fail. | ||
236 | */ | ||
237 | MHD_FOM_REQUIRE = 1 | ||
238 | }; | ||
239 | |||
240 | |||
241 | /** | ||
242 | * Configure TCP_FASTOPEN option, including setting a | ||
243 | * custom @a queue_length. | ||
244 | * | ||
245 | * Note that having a larger queue size can cause resource exhaustion | ||
246 | * attack as the TCP stack has to now allocate resources for the SYN | ||
247 | * packet along with its DATA. | ||
248 | * | ||
249 | * @param fom under which conditions should we use TCP_FASTOPEN? | ||
250 | * @param queue_length queue length to use, default is 50 if this | ||
251 | * option is never given. | ||
252 | * @return MHD option | ||
253 | */ | ||
254 | _MHD_EXTERN struct MHD_Option | ||
255 | MHD_option_tcp_fastopen (enum MHD_FastOpenMethod fom, | ||
256 | unsigned int queue_length); | ||
257 | |||
258 | |||
259 | /** | ||
260 | * Bind to the given TCP port. | ||
261 | * Ineffective in conjunction with #MHD_option_listen_socket(). | ||
262 | * Ineffective in conjunction with #MHD_option_bind_sa(). | ||
263 | * | ||
264 | * If neither this option nor the other two mentioned above | ||
265 | * is specified, MHD will simply not listen on any socket! | ||
266 | * | ||
267 | * @param port port to use, 0 to bind to a random (free) port | ||
268 | * @return MHD option | ||
269 | */ | ||
270 | _MHD_EXTERN struct MHD_Option | ||
271 | MHD_option_bind_port (uint16_t port); | ||
272 | |||
273 | |||
274 | /** | ||
275 | * Bind to the given socket address. | ||
276 | * Ineffective in conjunction with #MHD_option_listen_socket(). | ||
277 | * | ||
278 | * @return MHD option | ||
279 | */ | ||
280 | _MHD_EXTERN struct MHD_Option | ||
281 | MHD_option_bind_socket_address (const struct sockaddr *sa); | ||
282 | |||
283 | |||
284 | /** | ||
285 | * Use the given backlog for the listen() call. | ||
286 | * Ineffective in conjunction with #MHD_option_listen_socket(). | ||
287 | * | ||
288 | * @param listen_backlog backlog to use | ||
289 | * @return MHD option | ||
290 | */ | ||
291 | _MHD_EXTERN struct MHD_Option | ||
292 | MHD_option_listen_queue (int listen_backlog); | ||
293 | |||
294 | |||
295 | /** | ||
296 | * If present true, allow reusing address:port socket (by using | ||
297 | * SO_REUSEPORT on most platform, or platform-specific ways). If | ||
298 | * present and set to false, disallow reusing address:port socket | ||
299 | * (does nothing on most plaform, but uses SO_EXCLUSIVEADDRUSE on | ||
300 | * Windows). | ||
301 | * Ineffective in conjunction with #MHD_option_listen_socket(). | ||
302 | * | ||
303 | * @return MHD option | ||
304 | */ | ||
305 | _MHD_EXTERN struct MHD_Option | ||
306 | MHD_option_listen_allow_address_reuse (void); | ||
307 | |||
308 | |||
309 | /** | ||
310 | * Accept connections from the given socket. Socket | ||
311 | * must be a TCP or UNIX domain (stream) socket. | ||
312 | * | ||
313 | * Disables other listen options, including | ||
314 | * #MHD_option_bind_sa(), #MHD_option_bind_port(), | ||
315 | * #MHD_option_listen_queue() and | ||
316 | * #MHD_option_listen_allow_address_reuse(). | ||
317 | * | ||
318 | * @param listen_socket listen socket to use | ||
319 | * @return MHD option | ||
320 | */ | ||
321 | _MHD_EXTERN struct MHD_Option | ||
322 | MHD_option_listen_socket (int listen_socket); | ||
323 | |||
324 | |||
325 | /** | ||
326 | * Event loop syscalls supported by MHD. | ||
327 | */ | ||
328 | enum MHD_EventLoopSyscall | ||
329 | { | ||
330 | /** | ||
331 | * Automatic selection of best-available method. This is also the | ||
332 | * default. | ||
333 | */ | ||
334 | MHD_ELS_AUTO = 0, | ||
335 | |||
336 | /** | ||
337 | * Use select(). | ||
338 | */ | ||
339 | MHD_ELS_SELECT = 1, | ||
340 | |||
341 | /** | ||
342 | * Use poll(). | ||
343 | */ | ||
344 | MHD_ELS_POLL = 2, | ||
345 | |||
346 | /** | ||
347 | * Use epoll(). | ||
348 | */ | ||
349 | MHD_ELS_EPOLL = 3 | ||
350 | }; | ||
351 | |||
352 | |||
353 | /** | ||
354 | * Force use of a particular event loop system call. | ||
355 | * | ||
356 | * @param els event loop syscall to use | ||
357 | * @return MHD option | ||
358 | */ | ||
359 | _MHD_EXTERN struct MHD_Option | ||
360 | MHD_option_event_loop (enum MHD_EventLoopSyscall els); | ||
361 | |||
362 | |||
363 | /** | ||
364 | * Protocol strictness enforced by MHD on clients. | ||
365 | */ | ||
366 | enum MHD_ProtocolStrictLevel | ||
367 | { | ||
368 | /** | ||
369 | * Be particularly permissive about the protocol, allowing slight | ||
370 | * deviations that are technically not allowed by the | ||
371 | * RFC. Specifically, at the moment, this flag causes MHD to allow | ||
372 | * spaces in header field names. This is disallowed by the standard. | ||
373 | * It is not recommended to set this value on publicly available | ||
374 | * servers as it may potentially lower level of protection. | ||
375 | */ | ||
376 | MHD_SL_PERMISSIVE = -1, | ||
377 | |||
378 | /** | ||
379 | * Sane level of protocol enforcement for production use. | ||
380 | */ | ||
381 | MHD_SL_DEFAULT = 0, | ||
382 | |||
383 | /** | ||
384 | * Be strict about the protocol (as opposed to as tolerant as | ||
385 | * possible). Specifically, at the moment, this flag causes MHD to | ||
386 | * reject HTTP 1.1 connections without a "Host" header. This is | ||
387 | * required by the standard, but of course in violation of the "be | ||
388 | * as liberal as possible in what you accept" norm. It is | ||
389 | * recommended to set this if you are testing clients against | ||
390 | * MHD, and to use default in production. | ||
391 | */ | ||
392 | MHD_SL_STRICT = 1 | ||
393 | }; | ||
394 | |||
395 | |||
396 | /** | ||
397 | * Set how strictly MHD will enforce the HTTP protocol. | ||
398 | * | ||
399 | * @param sl how strict should we be | ||
400 | * @return MHD option | ||
401 | */ | ||
402 | _MHD_EXTERN struct MHD_Option | ||
403 | MHD_option_protocol_strict_level (enum MHD_ProtocolStrictLevel sl); | ||
404 | |||
405 | |||
406 | /** | ||
407 | * Enable TLS. | ||
408 | * | ||
409 | * @param tls_backend which TLS backend should be used, | ||
410 | * currently only "gnutls" is supported. You can | ||
411 | * also specify "NULL" for best-available (which is the default). | ||
412 | */ | ||
413 | _MHD_EXTERN struct MHD_Option | ||
414 | MHD_option_tls (const char *tls_backend); | ||
415 | |||
416 | |||
417 | /** | ||
418 | * Provide TLS key and certificate data in-memory. | ||
419 | * | ||
420 | * @param mem_key private key (key.pem) to be used by the | ||
421 | * HTTPS daemon. Must be the actual data in-memory, not a filename. | ||
422 | * @param mem_cert certificate (cert.pem) to be used by the | ||
423 | * HTTPS daemon. Must be the actual data in-memory, not a filename. | ||
424 | * @return MHD option | ||
425 | */ | ||
426 | _MHD_EXTERN struct MHD_Option | ||
427 | MHD_option_tls_key_and_cert_from_memory (const char *mem_key, | ||
428 | const char *mem_cert); | ||
429 | |||
430 | |||
431 | /** | ||
432 | * Provide passphrase to decrypt 'key.pem' (if required). | ||
433 | * | ||
434 | * @param pass passphrase phrase to decrypt 'key.pem' | ||
435 | */ | ||
436 | _MHD_EXTERN struct MHD_Option | ||
437 | MHD_option_tls_key_passphrase (const char *pass); | ||
438 | |||
439 | |||
440 | /** | ||
441 | * Configure TLS ciphers to use. Default is "NORMAL". | ||
442 | * | ||
443 | * @param ciphers which ciphers should be used by TLS | ||
444 | */ | ||
445 | _MHD_EXTERN struct MHD_Option | ||
446 | MHD_option_tls_ciphers (const char *ciphers); | ||
447 | |||
448 | |||
449 | /** | ||
450 | * Configure DH parameters (dh.pem) to use for the TLS key | ||
451 | * exchange. | ||
452 | * | ||
453 | * @param dh parameters to use | ||
454 | */ | ||
455 | _MHD_EXTERN struct MHD_Option | ||
456 | MHD_option_tls_mem_dhparams (const char *dh); | ||
457 | |||
458 | |||
459 | /** | ||
460 | * Memory pointer for the certificate (ca.pem) to be used by the | ||
461 | * HTTPS daemon for client authentification. | ||
462 | * | ||
463 | * @param mem_trust memory pointer to the certificate | ||
464 | */ | ||
465 | _MHD_EXTERN struct MHD_Option | ||
466 | MHD_option_tls_mem_trust (const char *mem_trust); | ||
467 | |||
468 | |||
469 | /** | ||
470 | * Configure daemon credentials type for GnuTLS. | ||
471 | * | ||
472 | * @param gnutls_credentials must be a value of | ||
473 | * type `gnutls_credentials_type_t` | ||
474 | */ | ||
475 | _MHD_EXTERN struct MHD_Option | ||
476 | MHD_option_gnutls_credentials (int gnutls_credentials); | ||
477 | |||
478 | |||
479 | /** | ||
480 | * Provide TLS key and certificate data via callback. | ||
481 | * | ||
482 | * Use a callback to determine which X.509 certificate should be used | ||
483 | * for a given HTTPS connection. This option provides an alternative | ||
484 | * to #MHD_option_tls_key_and_cert_from_memory(). You must use this | ||
485 | * version if multiple domains are to be hosted at the same IP address | ||
486 | * using TLS's Server Name Indication (SNI) extension. In this case, | ||
487 | * the callback is expected to select the correct certificate based on | ||
488 | * the SNI information provided. The callback is expected to access | ||
489 | * the SNI data using `gnutls_server_name_get()`. Using this option | ||
490 | * requires GnuTLS 3.0 or higher. | ||
491 | * | ||
492 | * @param cb must be of type `gnutls_certificate_retrieve_function2 *`. | ||
493 | * @return MHD option | ||
494 | */ | ||
495 | _MHD_EXTERN struct MHD_Option | ||
496 | MHD_option_gnutls_key_and_cert_from_callback (void *cb); | ||
497 | |||
498 | |||
499 | /** | ||
500 | * Run using a specific address family (by default, MHD will support | ||
501 | * dual stack if supported by the operating system). | ||
502 | * | ||
503 | * @param af address family to use, i.e. #AF_INET or #AF_INET6, | ||
504 | * or #AF_UNSPEC for dual stack | ||
505 | * @return MHD option | ||
506 | */ | ||
507 | _MHD_EXTERN struct MHD_Option | ||
508 | MHD_option_address_family (int af); | ||
509 | |||
510 | |||
511 | /** | ||
512 | * Enable use of one thread per connection. | ||
513 | * | ||
514 | * @return MHD option | ||
515 | */ | ||
516 | _MHD_EXTERN struct MHD_Option | ||
517 | MHD_option_thread_per_connection (void); | ||
518 | |||
519 | |||
520 | /** | ||
521 | * Enable use of MHD-internal worker thread. | ||
522 | * | ||
523 | * Run using an internal thread (or thread pool) for sockets sending | ||
524 | * and receiving and data processing. Without this flag MHD will not | ||
525 | * run automatically in background thread(s). If this option is set, | ||
526 | * #MHD_run() and #MHD_run_from_select() cannot be used. | ||
527 | * | ||
528 | * @return MHD option | ||
529 | */ | ||
530 | _MHD_EXTERN struct MHD_Option | ||
531 | MHD_option_thread_iternal (void); | ||
532 | |||
533 | |||
534 | /** | ||
535 | * Enable use of a thread pool of the given size. | ||
536 | * | ||
537 | * @param num_threads number of threads to run in the pool | ||
538 | * @return MHD option | ||
539 | */ | ||
540 | _MHD_EXTERN struct MHD_Option | ||
541 | MHD_option_thread_pool_size (unsigned int num_threads); | ||
542 | |||
543 | |||
544 | /** | ||
545 | * Allow or deny a client to connect. | ||
546 | * | ||
547 | * @param cls closure | ||
548 | * @param addr address information from the client | ||
549 | * @param addrlen length of @a addr | ||
550 | * @see #MHD_option_accept_policy() | ||
551 | * @return #MHD_YES if connection is allowed, #MHD_NO if not | ||
552 | */ | ||
553 | typedef enum MHD_Bool | ||
554 | (*MHD_AcceptPolicyCallback) (void *cls, | ||
555 | const struct sockaddr *addr, | ||
556 | socklen_t addrlen); | ||
557 | |||
558 | |||
559 | /** | ||
560 | * Return option setting a policy that accepts/rejects connections | ||
561 | * based on the client's IP address. This function will be called | ||
562 | * before a connection object is created. | ||
563 | * | ||
564 | * @param apc function to call to check the policy | ||
565 | * @param apc_cls closure for @a apc | ||
566 | */ | ||
567 | _MHD_EXTERN struct MHD_Option | ||
568 | MHD_option_accept_policy (MHD_AcceptPolicyCallback apc, | ||
569 | void *apc_cls); | ||
570 | |||
571 | |||
572 | /** | ||
573 | * Signature of the callback used by MHD to notify the | ||
574 | * application about started/stopped connections | ||
575 | * | ||
576 | * @param cls client-defined closure | ||
577 | * @param connection connection handle | ||
578 | * @param socket_context socket-specific pointer where the | ||
579 | * client can associate some state specific | ||
580 | * to the TCP connection; note that this is | ||
581 | * different from the "con_cls" which is per | ||
582 | * HTTP request. The client can initialize | ||
583 | * during #MHD_CONNECTION_NOTIFY_STARTED and | ||
584 | * cleanup during #MHD_CONNECTION_NOTIFY_CLOSED | ||
585 | * and access in the meantime using | ||
586 | * #MHD_CONNECTION_INFO_SOCKET_CONTEXT. | ||
587 | * @param toe reason for connection notification | ||
588 | * @see #MHD_OPTION_NOTIFY_CONNECTION | ||
589 | * @ingroup request | ||
590 | */ | ||
591 | typedef void | ||
592 | (*MHD_ConnectionCompletedCallback) (void *cls, | ||
593 | struct MHD_Connection *connection, | ||
594 | enum MHD_ConnectionNotificationCode toe); | ||
595 | |||
596 | |||
597 | /** | ||
598 | * Register a function that should be called whenever a connection is | ||
599 | * started or closed. | ||
600 | * | ||
601 | * @param ncc function to call to check the policy | ||
602 | * @param ncc_cls closure for @a apc | ||
603 | */ | ||
604 | _MHD_EXTERN struct MHD_Option | ||
605 | MHD_option_set_notify_connection (MHD_NotifyConnectionCallback ncc, | ||
606 | void *ncc_cls); | ||
607 | |||
608 | |||
609 | /** | ||
610 | * Maximum memory size per connection (followed by a `size_t`). | ||
611 | * Default is 32 kb (#MHD_POOL_SIZE_DEFAULT). | ||
612 | * Values above 128k are unlikely to result in much benefit, as half | ||
613 | * of the memory will be typically used for IO, and TCP buffers are | ||
614 | * unlikely to support window sizes above 64k on most systems. | ||
615 | * | ||
616 | * @param memory_limit_b connection memory limit to use in bytes | ||
617 | * @return MHD option | ||
618 | */ | ||
619 | _MHD_EXTERN struct MHD_Option | ||
620 | MHD_option_connection_memory_limit (size_t memory_limit_b); | ||
621 | |||
622 | |||
623 | /** | ||
624 | * Increment to use for growing the read buffer (followed by a | ||
625 | * `size_t`). Must fit within #MHD_option_connection_memory_limit()). | ||
626 | * | ||
627 | * @param memory_limit_b connection memory limit to use in bytes | ||
628 | * @return MHD option | ||
629 | */ | ||
630 | _MHD_EXTERN struct MHD_Option | ||
631 | MHD_option_connection_memory_increment (size_t memory_increment_b); | ||
632 | |||
633 | |||
634 | /** | ||
635 | * Desired size of the stack for threads created by MHD. Use 0 for | ||
636 | * system default. | ||
637 | * | ||
638 | * @param stack_limit_b stack size to use in bytes | ||
639 | * @return MHD option | ||
640 | */ | ||
641 | _MHD_EXTERN struct MHD_Option | ||
642 | MHD_option_thread_stack_size (size_t stack_limit_b); | ||
643 | |||
644 | |||
645 | /** | ||
646 | * Set maximum number of concurrent connections to accept. If not | ||
647 | * given, MHD will not enforce any global limit (modulo running into | ||
648 | * OS limits). | ||
649 | * | ||
650 | * @param connection_limit maximum number of concurrent connections | ||
651 | * @return MHD option | ||
652 | */ | ||
653 | _MHD_EXTERN struct MHD_Option | ||
654 | MHD_option_connection_global_limit (unsigned int connection_limit); | ||
655 | |||
656 | |||
657 | /** | ||
658 | * Limit on the number of (concurrent) connections made to the | ||
659 | * server from the same IP address. Can be used to prevent one | ||
660 | * IP from taking over all of the allowed connections. If the | ||
661 | * same IP tries to establish more than the specified number of | ||
662 | * connections, they will be immediately rejected. The default is | ||
663 | * zero, which means no limit on the number of connections | ||
664 | * from the same IP address. | ||
665 | * | ||
666 | * @param connection_limit maximum number of concurrent connections | ||
667 | * @return MHD option | ||
668 | */ | ||
669 | _MHD_EXTERN struct MHD_Option | ||
670 | MHD_option_connection_ip_limit (unsigned int connection_limit); | ||
671 | |||
672 | |||
673 | /** | ||
674 | * After how many seconds of inactivity should a | ||
675 | * connection automatically be timed out? | ||
676 | * Use zero for no timeout, which is also the (unsafe!) default. | ||
677 | * | ||
678 | * @param timeout_s number of seconds of timeout to use | ||
679 | * @return MHD option | ||
680 | */ | ||
681 | _MHD_EXTERN struct MHD_Option | ||
682 | MHD_option_connection_default_timeout (unsigned int timeout_s); | ||
683 | |||
684 | |||
685 | /** | ||
686 | * Signature of functions performing unescaping of strings. | ||
687 | * The return value must be "strlen(s)" and @a s should be | ||
688 | * updated. Note that the unescape function must not lengthen @a s | ||
689 | * (the result must be shorter than the input and still be | ||
690 | * 0-terminated). | ||
691 | * | ||
692 | * @param cls closure | ||
693 | * @param req the request for which unescaping is performed | ||
694 | * @param[in,out] s string to unescape | ||
695 | * @return number of characters in @a s (excluding 0-terminator) | ||
696 | */ | ||
697 | typedef size_t | ||
698 | MHD_UnescapeCallback (void *cls, | ||
699 | struct MHD_Request *req, | ||
700 | char *s); | ||
701 | |||
702 | |||
703 | /** | ||
704 | * Specify a function that should be called for unescaping escape | ||
705 | * sequences in URIs and URI arguments. Note that this function | ||
706 | * will NOT be used by the `struct MHD_PostProcessor`. If this | ||
707 | * option is not specified, the default method will be used which | ||
708 | * decodes escape sequences of the form "%HH". | ||
709 | * | ||
710 | * @param unescape_cb function to use, NULL for default | ||
711 | * @param unescape_cb_cls closure for @a unescape_cb | ||
712 | * @return MHD option | ||
713 | */ | ||
714 | _MHD_EXTERN struct MHD_Option | ||
715 | MHD_option_unescape_cb (MHD_UnescapeCallback unescape_cb, | ||
716 | void *unescape_cb_cls); | ||
717 | |||
718 | |||
719 | /** | ||
720 | * Set random values to be used by the Digest Auth module. Note that | ||
721 | * the application must ensure that @a buf remains allocated and | ||
722 | * unmodified while the deamon is running. | ||
723 | * | ||
724 | * @param buf_size number of bytes in @a buf | ||
725 | * @param buf entropy buffer | ||
726 | * @return MHD option | ||
727 | */ | ||
728 | _MHD_EXTERN struct MHD_Option | ||
729 | MHD_option_digest_auth_random (size_t buf_size, | ||
730 | const void *buf); | ||
731 | |||
732 | |||
733 | /** | ||
734 | * Size of the internal array holding the map of the nonce and | ||
735 | * the nonce counter. | ||
736 | * | ||
737 | * @param nc_length desired array length | ||
738 | * @return MHD option | ||
739 | */ | ||
740 | _MHD_EXTERN struct MHD_Option | ||
741 | MHD_option_digest_auth_nc_size (size_t stack_limit_b); | ||
742 | |||
743 | |||
744 | /** | ||
745 | * Return option setting a callback to call upon connection | ||
746 | * completion. | ||
747 | * | ||
748 | * @param ccc function to call | ||
749 | * @param ccc_cls closure for @a ccc | ||
750 | */ | ||
751 | _MHD_EXTERN struct MHD_Option | ||
752 | MHD_option_connection_completion (MHD_ConnectionCompledCallback ccc, | ||
753 | void *ccc_cls;) | ||
754 | |||
755 | |||
756 | /** | ||
757 | * Signature of the callback used by MHD to notify the application | ||
758 | * that we have received the full header of a request. Can be used to | ||
759 | * send error responses to a "Expect: 100-continue" request. | ||
760 | * Note that regular responses should be set in the | ||
761 | * #MHD_RequestCompletedCallback. | ||
762 | * | ||
763 | * @param cls client-defined closure | ||
764 | * @ingroup request | ||
765 | * @return #MHD_YES if the upload was handled successfully, | ||
766 | * #MHD_NO if the socket must be closed due to a serios | ||
767 | * error while handling the request | ||
768 | */ | ||
769 | typedef enum MHD_Bool | ||
770 | (*MHD_RequestHeaderCallback) (void *cls); | ||
771 | |||
772 | |||
773 | /** | ||
774 | * A client has uploaded data. | ||
775 | * | ||
776 | * @param cls argument given together with the function | ||
777 | * pointer when the handler was registered with MHD | ||
778 | * @param upload_data the data being uploaded (excluding HEADERS, | ||
779 | * for a POST that fits into memory and that is encoded | ||
780 | * with a supported encoding, the POST data will NOT be | ||
781 | * given in upload_data and is instead available as | ||
782 | * part of #MHD_get_connection_values; very large POST | ||
783 | * data *will* be made available incrementally in | ||
784 | * @a upload_data) | ||
785 | * @param[in,out] upload_data_size set initially to the size of the | ||
786 | * @a upload_data provided; the method must update this | ||
787 | * value to the number of bytes NOT processed; | ||
788 | * @return #MHD_YES if the upload was handled successfully, | ||
789 | * #MHD_NO if the socket must be closed due to a serios | ||
790 | * error while handling the request | ||
791 | */ | ||
792 | typedef enum MHD_Bool | ||
793 | (*MHD_UploadCallback) (void *cls, | ||
794 | const char *upload_data, | ||
795 | size_t *upload_data_size); | ||
796 | |||
797 | |||
798 | /** | ||
799 | * Signature of the callback used by MHD to notify the application | ||
800 | * that we now expect a response. The application can either | ||
801 | * call #MHD_response_queue() or suspend the request or return | ||
802 | * #MHD_NO. | ||
803 | * | ||
804 | * @param cls client-defined closure | ||
805 | * @ingroup request | ||
806 | * @return #MHD_YES if the upload was handled successfully, | ||
807 | * #MHD_NO if the socket must be closed due to a serios | ||
808 | * error while handling the request | ||
809 | */ | ||
810 | typedef enum MHD_Bool | ||
811 | (*MHD_RequestFetchResponseCallback) (void *cls); | ||
812 | |||
813 | |||
814 | /** | ||
815 | * Signature of the callback used by MHD to notify the | ||
816 | * application about completed requests. | ||
817 | * | ||
818 | * @param cls client-defined closure | ||
819 | * @param toe reason for request termination | ||
820 | * @see #MHD_option_request_completion() | ||
821 | * @ingroup request | ||
822 | */ | ||
823 | typedef void | ||
824 | (*MHD_RequestCompletedCallback) (void *cls, | ||
825 | enum MHD_RequestTerminationCode toe); | ||
826 | |||
827 | |||
828 | /** | ||
829 | * Functions called for an MHD request to process it. | ||
830 | * Not all functions must be implemented for each request. | ||
831 | */ | ||
832 | struct MHD_RequestHandlerCallbacks | ||
833 | { | ||
834 | /** | ||
835 | * Closure argument passed to all callbacks in this struct. | ||
836 | */ | ||
837 | void *cls; | ||
838 | |||
839 | /** | ||
840 | * Function called after we have received the full HTTP header. | ||
841 | */ | ||
842 | MHD_RequestHeaderCallback header_cb; | ||
843 | |||
844 | /** | ||
845 | * Function called if we receive uploaded data. | ||
846 | */ | ||
847 | MHD_UploadCallback upload_cb; | ||
848 | |||
849 | /** | ||
850 | * Function called when we expect the application to | ||
851 | * generate a response (mandatory to be set; if not | ||
852 | * set and #MHD_NO is not returned, MHD will generate | ||
853 | * 500 internal error and log an error). | ||
854 | */ | ||
855 | MHD_RequestFetchResponseCallback fetch_response_cb; | ||
856 | |||
857 | /** | ||
858 | * Function called last to clean up. Gives the | ||
859 | * application a chance to check on the final status of | ||
860 | * the request (and to clean up @e cls). | ||
861 | */ | ||
862 | MHD_RequestCompletedCallback completed_cb; | ||
863 | |||
864 | }; | ||
865 | |||
866 | |||
867 | /** | ||
868 | * A client has requested the given url using the given method | ||
869 | * (#MHD_HTTP_METHOD_GET, #MHD_HTTP_METHOD_PUT, | ||
870 | * #MHD_HTTP_METHOD_DELETE, #MHD_HTTP_METHOD_POST, etc). The callback | ||
871 | * must initialize @a rhp to provide further callbacks which will | ||
872 | * process the request further and ultimately to provide the response | ||
873 | * to give back to the client. | ||
874 | * | ||
875 | * @param cls argument given together with the function | ||
876 | * pointer when the handler was registered with MHD | ||
877 | * @param url the requested url (without arguments after "?") | ||
878 | * @param method the HTTP method used (#MHD_HTTP_METHOD_GET, | ||
879 | * #MHD_HTTP_METHOD_PUT, etc.) | ||
880 | * @param[out] must be set to function pointers to be used to | ||
881 | * handle the request further; can be assumed to have | ||
882 | * been initialized to all-NULL values already. | ||
883 | * @return #MHD_YES if the request was handled successfully, | ||
884 | * #MHD_NO if the socket must be closed due to a serios | ||
885 | * error while handling the request | ||
886 | */ | ||
887 | typedef enum MHD_Bool | ||
888 | (*MHD_RequestCallback) (void *cls, | ||
889 | struct MHD_Request *request, | ||
890 | const char *url, | ||
891 | const char *method, | ||
892 | struct MHD_RequestHandlerCallbacks *rhp); | ||
893 | |||
894 | |||
895 | /** | ||
896 | * Generic option to set a global URL handler which | ||
897 | * will be called for all requests. You may prefer the | ||
898 | * more convenient, but less generic #MHD_option_url_table(). | ||
899 | * | ||
900 | * @param rc function to call for requests | ||
901 | * @param rc_cls closure to give to @a rc | ||
902 | */ | ||
903 | _MHD_EXTERN struct MHD_Option | ||
904 | MHD_option_url_handler (MHD_RequestCallback rc, | ||
905 | void *rc_cls); | ||
906 | |||
907 | |||
908 | /** | ||
909 | * A client has requested the given url using the given method | ||
910 | * (#MHD_HTTP_METHOD_GET, #MHD_HTTP_METHOD_PUT, | ||
911 | * #MHD_HTTP_METHOD_DELETE, #MHD_HTTP_METHOD_POST, etc). The callback | ||
912 | * must initialize @a rhp to provide further callbacks which will | ||
913 | * process the request further and ultimately to provide the response | ||
914 | * to give back to the client. | ||
915 | * | ||
916 | * @param cls argument given together with the function | ||
917 | * pointer when the handler was registered with MHD | ||
918 | * @param request HTTP request handle | ||
919 | * @param[out] must be set to function pointers to be used to | ||
920 | * handle the request further; can be assumed to have | ||
921 | * been initialized to all-NULL values already. | ||
922 | * @return #MHD_YES if the request was handled successfully, | ||
923 | * #MHD_NO if the socket must be closed due to a serious | ||
924 | * error while handling the request | ||
925 | */ | ||
926 | typedef enum MHD_Bool | ||
927 | (*MHD_RequestStartCallback) (void *cls, | ||
928 | struct MHD_Request *request, | ||
929 | struct MHD_RequestHandlerCallbacks *rhp); | ||
930 | |||
931 | |||
932 | /** | ||
933 | * Definition of a request handler for a URL and method. | ||
934 | */ | ||
935 | struct MHD_UrlHandler; | ||
936 | |||
937 | |||
938 | /** | ||
939 | * Create URL handler array terminator. | ||
940 | */ | ||
941 | _MHD_EXTERN struct MHD_UrlHandler | ||
942 | MHD_url_handler_end (void); | ||
943 | |||
944 | |||
945 | /** | ||
946 | * Create a generic URL handler array entry. | ||
947 | * | ||
948 | * @param method HTTP method to which this handler | ||
949 | * matches. Case-insensitive, i.e. "GET". | ||
950 | * @param url Which URL does this handler match. Case-sensitive, | ||
951 | * i.e. "/favicon.ico". | ||
952 | * @param start_cb function to call for matching requests | ||
953 | * @param start_cb_cls closure for @a start_cb | ||
954 | * @return url handler array entry | ||
955 | */ | ||
956 | _MHD_EXTERN struct MHD_UrlHandler | ||
957 | MHD_url_handler_generic (const char *method, | ||
958 | const char *url, | ||
959 | MHD_RequestStartCallback start_cb, | ||
960 | void *start_cb_cls); | ||
961 | |||
962 | |||
963 | /** | ||
964 | * Create a simple URL handler array entry for requests | ||
965 | * where the application simply returns a response and | ||
966 | * has no state to initialize or clean up and where there | ||
967 | * is no upload. | ||
968 | * | ||
969 | * @param method HTTP method to which this handler | ||
970 | * matches. Case-insensitive, i.e. "GET". | ||
971 | * @param url Which URL does this handler match. Case-sensitive, | ||
972 | * i.e. "/favicon.ico". | ||
973 | * @param fetch_cb function to call for matching requests | ||
974 | * @param fetch_cb_cls closure for @a fetch_cb | ||
975 | * @return url handler array entry | ||
976 | */ | ||
977 | _MHD_EXTERN struct MHD_UrlHandler | ||
978 | MHD_url_handler_simple (const char *method, | ||
979 | const char *url, | ||
980 | MHD_RequestFetchResponseCallback fetch_cb, | ||
981 | void *fetch_cb_cls); | ||
982 | |||
983 | |||
984 | /** | ||
985 | * Set a table of @a handlers to process requests of matching methods | ||
986 | * and URLs. Requests that do not match any entry will yield a 404 | ||
987 | * NOT FOUND response. Note that this function may sort the @a | ||
988 | * handlers array in-place for faster (logarithmic) lookups later, | ||
989 | * hence the argument must be muteable. The @a handlers array must | ||
990 | * remain allocated by the application throughout the lifetime of the | ||
991 | * daemon! | ||
992 | * | ||
993 | * @param[in,out] handlers url handler table, terminated | ||
994 | * by #MHD_url_handler_end() | ||
995 | * @return option array entry | ||
996 | */ | ||
997 | _MHD_EXTERN struct MHD_Option | ||
998 | MHD_option_url_table (struct MHD_UrlHandler handlers[]); | ||
999 | |||
1000 | |||
1001 | /* **************** Daemon handling functions ***************** */ | ||
1002 | |||
1003 | /** | ||
1004 | * Start a webserver on the given port. | ||
1005 | * | ||
1006 | * @param options array of options, does NOT have to | ||
1007 | * persist in memory past this call (note that individual | ||
1008 | * arguments passed to the functions may need to | ||
1009 | * be preserved) | ||
1010 | * @return NULL on error, handle to daemon on success | ||
1011 | * @ingroup event | ||
1012 | */ | ||
1013 | _MHD_EXTERN struct MHD_Daemon * | ||
1014 | MHD_daemon_start (const struct MHD_Option options[]); | ||
1015 | |||
1016 | |||
1017 | /** | ||
1018 | * Stop accepting connections from the listening socket. Allows | ||
1019 | * clients to continue processing, but stops accepting new | ||
1020 | * connections. Note that the caller is responsible for closing the | ||
1021 | * returned socket; however, if MHD is run using threads (anything but | ||
1022 | * external select mode), it must not be closed until AFTER | ||
1023 | * #MHD_stop_daemon has been called (as it is theoretically possible | ||
1024 | * that an existing thread is still using it). | ||
1025 | * | ||
1026 | * Note that some thread modes require the caller to have passed | ||
1027 | * #MHD_USE_ITC when using this API. If this daemon is | ||
1028 | * in one of those modes and this option was not given to | ||
1029 | * #MHD_start_daemon, this function will return #MHD_INVALID_SOCKET. | ||
1030 | * | ||
1031 | * @param daemon daemon to stop accepting new connections for | ||
1032 | * @return old listen socket on success, #MHD_INVALID_SOCKET if | ||
1033 | * the daemon was already not listening anymore | ||
1034 | * @ingroup specialized | ||
1035 | */ | ||
1036 | _MHD_EXTERN MHD_socket | ||
1037 | MHD_daemon_quiesce (struct MHD_Daemon *daemon); | ||
1038 | |||
1039 | |||
1040 | /** | ||
1041 | * Shutdown an HTTP daemon. | ||
1042 | * | ||
1043 | * @param daemon daemon to stop | ||
1044 | * @ingroup event | ||
1045 | */ | ||
1046 | _MHD_EXTERN void | ||
1047 | MHD_daemon_stop (struct MHD_Daemon *daemon); | ||
1048 | |||
1049 | |||
1050 | /* ********************* connection options ************** */ | ||
1051 | |||
1052 | /** | ||
1053 | * MHD connection options. Given to #MHD_set_connection_option() to | ||
1054 | * set custom options for a particular connection. | ||
1055 | */ | ||
1056 | struct MHD_ConnectionOption; | ||
1057 | |||
1058 | |||
1059 | /** | ||
1060 | * Generate array terminator for connection options. | ||
1061 | */ | ||
1062 | struct MHD_ConnectionOption | ||
1063 | MHD_connection_option_end (void); | ||
1064 | |||
1065 | |||
1066 | /** | ||
1067 | * Generate option to set a custom timeout for the given connection. | ||
1068 | * Specified as the number of seconds. Use zero for no timeout. If | ||
1069 | * timeout was set to zero (or unset) before, setting of a new value | ||
1070 | * by MHD_connection_set_option() will reset timeout timer. | ||
1071 | * | ||
1072 | * @param timeout_s new timeout in seconds | ||
1073 | */ | ||
1074 | struct MHD_ConnectionOption | ||
1075 | MHD_connection_option_timeout (unsigned int timeout_s); | ||
1076 | |||
1077 | |||
1078 | /** | ||
1079 | * Set a custom option for the given connection, overriding defaults. | ||
1080 | * | ||
1081 | * @param connection connection to modify | ||
1082 | * @param options array of options to set, does NOT have to | ||
1083 | * persist past this call | ||
1084 | * @ingroup specialized | ||
1085 | * @return #MHD_YES on success | ||
1086 | */ | ||
1087 | _MHD_EXTERN enum MHD_Bool | ||
1088 | MHD_connection_set_options (struct MHD_Connection *connection, | ||
1089 | struct MHD_ConnectionOption options[]); | ||
1090 | |||
1091 | |||
1092 | /* **************** Request handling functions ***************** */ | ||
1093 | |||
1094 | /** | ||
1095 | * Get all of the headers from the request. | ||
1096 | * | ||
1097 | * @param request request to get values from | ||
1098 | * @param kind types of values to iterate over, can be a bitmask | ||
1099 | * @param iterator callback to call on each header; | ||
1100 | * maybe NULL (then just count headers) | ||
1101 | * @param iterator_cls extra argument to @a iterator | ||
1102 | * @return number of entries iterated over | ||
1103 | * @ingroup request | ||
1104 | */ | ||
1105 | _MHD_EXTERN unsigned int | ||
1106 | MHD_request_get_values (struct MHD_Request *request, | ||
1107 | enum MHD_ValueKind kind, | ||
1108 | MHD_KeyValueIterator iterator, | ||
1109 | void *iterator_cls); | ||
1110 | |||
1111 | |||
1112 | /** | ||
1113 | * This function can be used to add an entry to the HTTP headers of a | ||
1114 | * request (so that the #MHD_request_get_values function will | ||
1115 | * return them -- and the `struct MHD_PostProcessor` will also see | ||
1116 | * them). This maybe required in certain situations (see Mantis | ||
1117 | * #1399) where (broken) HTTP implementations fail to supply values | ||
1118 | * needed by the post processor (or other parts of the application). | ||
1119 | * | ||
1120 | * This function MUST only be called from within the | ||
1121 | * request callbacks (otherwise, access maybe improperly | ||
1122 | * synchronized). Furthermore, the client must guarantee that the key | ||
1123 | * and value arguments are 0-terminated strings that are NOT freed | ||
1124 | * until the connection is closed. (The easiest way to do this is by | ||
1125 | * passing only arguments to permanently allocated strings.). | ||
1126 | * | ||
1127 | * @param request the request for which a | ||
1128 | * value should be set | ||
1129 | * @param kind kind of the value | ||
1130 | * @param key key for the value | ||
1131 | * @param value the value itself | ||
1132 | * @return #MHD_NO if the operation could not be | ||
1133 | * performed due to insufficient memory; | ||
1134 | * #MHD_YES on success | ||
1135 | * @ingroup request | ||
1136 | */ | ||
1137 | _MHD_EXTERN enum MHD_Bool | ||
1138 | MHD_request_set_value (struct MHD_Request *request, | ||
1139 | enum MHD_ValueKind kind, | ||
1140 | const char *key, | ||
1141 | const char *value); | ||
1142 | |||
1143 | |||
1144 | /** | ||
1145 | * Get a particular header value. If multiple | ||
1146 | * values match the kind, return any one of them. | ||
1147 | * | ||
1148 | * @param request request to get values from | ||
1149 | * @param kind what kind of value are we looking for | ||
1150 | * @param key the header to look for, NULL to lookup 'trailing' value without a key | ||
1151 | * @return NULL if no such item was found | ||
1152 | * @ingroup request | ||
1153 | */ | ||
1154 | _MHD_EXTERN const char * | ||
1155 | MHD_request_lookup_value (struct MHD_Request *request, | ||
1156 | enum MHD_ValueKind kind, | ||
1157 | const char *key); | ||
1158 | |||
1159 | |||
1160 | /** | ||
1161 | * Queue a response to be transmitted to the client (as soon as | ||
1162 | * possible but after the current callback returns). | ||
1163 | * | ||
1164 | * @param request the request identifying the client | ||
1165 | * @param status_code HTTP status code (i.e. #MHD_HTTP_OK) | ||
1166 | * @param response response to transmit | ||
1167 | * @return #MHD_NO on error (i.e. reply already sent), | ||
1168 | * #MHD_YES on success or if message has been queued | ||
1169 | * @ingroup response | ||
1170 | */ | ||
1171 | _MHD_EXTERN int | ||
1172 | MHD_request_queue_response (struct MHD_Request *request, | ||
1173 | unsigned int status_code, | ||
1174 | struct MHD_Response *response); | ||
1175 | |||
1176 | |||
1177 | /** | ||
1178 | * Suspend handling of network data for a given request. This can | ||
1179 | * be used to dequeue a request from MHD's event loop for a while. | ||
1180 | * | ||
1181 | * If you use this API in conjunction with a internal select or a | ||
1182 | * thread pool, you must set the option #MHD_USE_ITC to | ||
1183 | * ensure that a resumed request is immediately processed by MHD. | ||
1184 | * | ||
1185 | * Suspended requests continue to count against the total number of | ||
1186 | * requests allowed (per daemon, as well as per IP, if such limits | ||
1187 | * are set). Suspended requests will NOT time out; timeouts will | ||
1188 | * restart when the request handling is resumed. While a | ||
1189 | * request is suspended, MHD will not detect disconnects by the | ||
1190 | * client. | ||
1191 | * | ||
1192 | * The only safe time to suspend a request is from the | ||
1193 | * #MHD_AccessHandlerCallback. | ||
1194 | * | ||
1195 | * Finally, it is an API violation to call #MHD_stop_daemon while | ||
1196 | * having suspended requests (this will at least create memory and | ||
1197 | * socket leaks or lead to undefined behavior). You must explicitly | ||
1198 | * resume all requests before stopping the daemon. | ||
1199 | * | ||
1200 | * @param request the request to suspend | ||
1201 | */ | ||
1202 | _MHD_EXTERN void | ||
1203 | MHD_request_suspend (struct MHD_Request *request); | ||
1204 | |||
1205 | |||
1206 | /** | ||
1207 | * Resume handling of network data for suspended request. It is | ||
1208 | * safe to resume a suspended request at any time. Calling this | ||
1209 | * function on a request that was not previously suspended will | ||
1210 | * result in undefined behavior. | ||
1211 | * | ||
1212 | * If you are using this function in ``external'' select mode, you must | ||
1213 | * make sure to run #MHD_run() afterwards (before again calling | ||
1214 | * #MHD_get_fdset(), as otherwise the change may not be reflected in | ||
1215 | * the set returned by #MHD_get_fdset() and you may end up with a | ||
1216 | * request that is stuck until the next network activity. | ||
1217 | * | ||
1218 | * @param request the request to resume | ||
1219 | */ | ||
1220 | _MHD_EXTERN void | ||
1221 | MHD_request_resume (struct MHD_Request *request); | ||
1222 | |||
1223 | |||
1224 | /* **************** Response manipulation functions ***************** */ | ||
1225 | |||
1226 | |||
1227 | /** | ||
1228 | * MHD response option. | ||
1229 | */ | ||
1230 | struct MHD_ResponseOption; | ||
1231 | |||
1232 | |||
1233 | /** | ||
1234 | * End of options array. | ||
1235 | */ | ||
1236 | struct MHD_ResponseOption | ||
1237 | MHD_response_option_end (void); | ||
1238 | |||
1239 | |||
1240 | /** | ||
1241 | * Only respond in conservative HTTP 1.0-mode. In particular, | ||
1242 | * do not (automatically) sent "Connection" headers and always | ||
1243 | * close the connection after generating the response. | ||
1244 | */ | ||
1245 | struct MHD_ResponseOption | ||
1246 | MHD_response_option_v10_only (void); | ||
1247 | |||
1248 | |||
1249 | /** | ||
1250 | * Set special @a options for a @a response. | ||
1251 | * | ||
1252 | * @param response the response to modify | ||
1253 | * @param options options to set for the response | ||
1254 | * @return #MHD_YES on success, #MHD_NO on error | ||
1255 | */ | ||
1256 | _MHD_EXTERN enum MHD_Bool | ||
1257 | MHD_response_set_options (struct MHD_Response *response, | ||
1258 | enum MHD_ResponseOption options[]); | ||
1259 | |||
1260 | |||
1261 | /** | ||
1262 | * Create a response object. The response object can be extended with | ||
1263 | * header information and then be used any number of times. | ||
1264 | * | ||
1265 | * @param size size of the data portion of the response, #MHD_SIZE_UNKNOWN for unknown | ||
1266 | * @param block_size preferred block size for querying crc (advisory only, | ||
1267 | * MHD may still call @a crc using smaller chunks); this | ||
1268 | * is essentially the buffer size used for IO, clients | ||
1269 | * should pick a value that is appropriate for IO and | ||
1270 | * memory performance requirements | ||
1271 | * @param crc callback to use to obtain response data | ||
1272 | * @param crc_cls extra argument to @a crc | ||
1273 | * @param crfc callback to call to free @a crc_cls resources | ||
1274 | * @return NULL on error (i.e. invalid arguments, out of memory) | ||
1275 | * @ingroup response | ||
1276 | */ | ||
1277 | _MHD_EXTERN struct MHD_Response * | ||
1278 | MHD_response_from_callback (uint64_t size, | ||
1279 | size_t block_size, | ||
1280 | MHD_ContentReaderCallback crc, | ||
1281 | void *crc_cls, | ||
1282 | MHD_ContentReaderFreeCallback crfc); | ||
1283 | |||
1284 | |||
1285 | /** | ||
1286 | * Specification for how MHD should treat the memory buffer | ||
1287 | * given for the response. | ||
1288 | * @ingroup response | ||
1289 | */ | ||
1290 | enum MHD_ResponseMemoryMode | ||
1291 | { | ||
1292 | |||
1293 | /** | ||
1294 | * Buffer is a persistent (static/global) buffer that won't change | ||
1295 | * for at least the lifetime of the response, MHD should just use | ||
1296 | * it, not free it, not copy it, just keep an alias to it. | ||
1297 | * @ingroup response | ||
1298 | */ | ||
1299 | MHD_RESPMEM_PERSISTENT, | ||
1300 | |||
1301 | /** | ||
1302 | * Buffer is heap-allocated with `malloc()` (or equivalent) and | ||
1303 | * should be freed by MHD after processing the response has | ||
1304 | * concluded (response reference counter reaches zero). | ||
1305 | * @ingroup response | ||
1306 | */ | ||
1307 | MHD_RESPMEM_MUST_FREE, | ||
1308 | |||
1309 | /** | ||
1310 | * Buffer is in transient memory, but not on the heap (for example, | ||
1311 | * on the stack or non-`malloc()` allocated) and only valid during the | ||
1312 | * call to #MHD_create_response_from_buffer. MHD must make its | ||
1313 | * own private copy of the data for processing. | ||
1314 | * @ingroup response | ||
1315 | */ | ||
1316 | MHD_RESPMEM_MUST_COPY | ||
1317 | |||
1318 | }; | ||
1319 | |||
1320 | |||
1321 | /** | ||
1322 | * Create a response object. The response object can be extended with | ||
1323 | * header information and then be used any number of times. | ||
1324 | * | ||
1325 | * @param size size of the data portion of the response | ||
1326 | * @param buffer size bytes containing the response's data portion | ||
1327 | * @param mode flags for buffer management | ||
1328 | * @return NULL on error (i.e. invalid arguments, out of memory) | ||
1329 | * @ingroup response | ||
1330 | */ | ||
1331 | _MHD_EXTERN struct MHD_Response * | ||
1332 | MHD_response_from_buffer (size_t size, | ||
1333 | void *buffer, | ||
1334 | enum MHD_ResponseMemoryMode mode); | ||
1335 | |||
1336 | |||
1337 | /** | ||
1338 | * Create a response object based on an @a fd from which | ||
1339 | * data is read. The response object can be extended with | ||
1340 | * header information and then be used any number of times. | ||
1341 | * | ||
1342 | * @param fd file descriptor referring to a file on disk with the | ||
1343 | * data; will be closed when response is destroyed; | ||
1344 | * fd should be in 'blocking' mode | ||
1345 | * @param offset offset to start reading from in the file; | ||
1346 | * reading file beyond 2 GiB may be not supported by OS or | ||
1347 | * MHD build; see ::MHD_FEATURE_LARGE_FILE | ||
1348 | * @param size size of the data portion of the response; | ||
1349 | * sizes larger than 2 GiB may be not supported by OS or | ||
1350 | * MHD build; see ::MHD_FEATURE_LARGE_FILE | ||
1351 | * @return NULL on error (i.e. invalid arguments, out of memory) | ||
1352 | * @ingroup response | ||
1353 | */ | ||
1354 | _MHD_EXTERN struct MHD_Response * | ||
1355 | MHD_response_from_fd (int fd, | ||
1356 | uint64_t offset, | ||
1357 | uint64_t size); | ||
1358 | |||
1359 | |||
1360 | /** | ||
1361 | * Enumeration for actions MHD should perform on the underlying socket | ||
1362 | * of the upgrade. This API is not finalized, and in particular | ||
1363 | * the final set of actions is yet to be decided. This is just an | ||
1364 | * idea for what we might want. | ||
1365 | */ | ||
1366 | enum MHD_UpgradeAction | ||
1367 | { | ||
1368 | |||
1369 | /** | ||
1370 | * Close the socket, the application is done with it. | ||
1371 | * | ||
1372 | * Takes no extra arguments. | ||
1373 | */ | ||
1374 | MHD_UPGRADE_ACTION_CLOSE = 0 | ||
1375 | |||
1376 | }; | ||
1377 | |||
1378 | |||
1379 | /** | ||
1380 | * Handle given to the application to manage special | ||
1381 | * actions relating to MHD responses that "upgrade" | ||
1382 | * the HTTP protocol (i.e. to WebSockets). | ||
1383 | */ | ||
1384 | struct MHD_UpgradeResponseHandle; | ||
1385 | |||
1386 | |||
1387 | /** | ||
1388 | * This connection-specific callback is provided by MHD to | ||
1389 | * applications (unusual) during the #MHD_UpgradeHandler. | ||
1390 | * It allows applications to perform 'special' actions on | ||
1391 | * the underlying socket from the upgrade. | ||
1392 | * | ||
1393 | * @param urh the handle identifying the connection to perform | ||
1394 | * the upgrade @a action on. | ||
1395 | * @param action which action should be performed | ||
1396 | * @param ... arguments to the action (depends on the action) | ||
1397 | * @return #MHD_NO on error, #MHD_YES on success | ||
1398 | */ | ||
1399 | _MHD_EXTERN enum MHD_Bool | ||
1400 | MHD_upgrade_action (struct MHD_UpgradeResponseHandle *urh, | ||
1401 | enum MHD_UpgradeAction action, | ||
1402 | ...); | ||
1403 | |||
1404 | |||
1405 | /** | ||
1406 | * Function called after a protocol "upgrade" response was sent | ||
1407 | * successfully and the socket should now be controlled by some | ||
1408 | * protocol other than HTTP. | ||
1409 | * | ||
1410 | * Any data already received on the socket will be made available in | ||
1411 | * @e extra_in. This can happen if the application sent extra data | ||
1412 | * before MHD send the upgrade response. The application should | ||
1413 | * treat data from @a extra_in as if it had read it from the socket. | ||
1414 | * | ||
1415 | * Note that the application must not close() @a sock directly, | ||
1416 | * but instead use #MHD_upgrade_action() for special operations | ||
1417 | * on @a sock. | ||
1418 | * | ||
1419 | * Data forwarding to "upgraded" @a sock will be started as soon | ||
1420 | * as this function return. | ||
1421 | * | ||
1422 | * Except when in 'thread-per-connection' mode, implementations | ||
1423 | * of this function should never block (as it will still be called | ||
1424 | * from within the main event loop). | ||
1425 | * | ||
1426 | * @param cls closure, whatever was given to #MHD_create_response_for_upgrade(). | ||
1427 | * @param connection original HTTP connection handle, | ||
1428 | * giving the function a last chance | ||
1429 | * to inspect the original HTTP request | ||
1430 | * @param con_cls last value left in `con_cls` of the `MHD_AccessHandlerCallback` | ||
1431 | * @param extra_in if we happened to have read bytes after the | ||
1432 | * HTTP header already (because the client sent | ||
1433 | * more than the HTTP header of the request before | ||
1434 | * we sent the upgrade response), | ||
1435 | * these are the extra bytes already read from @a sock | ||
1436 | * by MHD. The application should treat these as if | ||
1437 | * it had read them from @a sock. | ||
1438 | * @param extra_in_size number of bytes in @a extra_in | ||
1439 | * @param sock socket to use for bi-directional communication | ||
1440 | * with the client. For HTTPS, this may not be a socket | ||
1441 | * that is directly connected to the client and thus certain | ||
1442 | * operations (TCP-specific setsockopt(), getsockopt(), etc.) | ||
1443 | * may not work as expected (as the socket could be from a | ||
1444 | * socketpair() or a TCP-loopback). The application is expected | ||
1445 | * to perform read()/recv() and write()/send() calls on the socket. | ||
1446 | * The application may also call shutdown(), but must not call | ||
1447 | * close() directly. | ||
1448 | * @param urh argument for #MHD_upgrade_action()s on this @a connection. | ||
1449 | * Applications must eventually use this callback to (indirectly) | ||
1450 | * perform the close() action on the @a sock. | ||
1451 | */ | ||
1452 | typedef void | ||
1453 | (*MHD_UpgradeHandler)(void *cls, | ||
1454 | struct MHD_Connection *connection, | ||
1455 | void *con_cls, | ||
1456 | const char *extra_in, | ||
1457 | size_t extra_in_size, | ||
1458 | MHD_socket sock, | ||
1459 | struct MHD_UpgradeResponseHandle *urh); | ||
1460 | |||
1461 | |||
1462 | /** | ||
1463 | * Create a response object that can be used for 101 UPGRADE | ||
1464 | * responses, for example to implement WebSockets. After sending the | ||
1465 | * response, control over the data stream is given to the callback (which | ||
1466 | * can then, for example, start some bi-directional communication). | ||
1467 | * If the response is queued for multiple connections, the callback | ||
1468 | * will be called for each connection. The callback | ||
1469 | * will ONLY be called after the response header was successfully passed | ||
1470 | * to the OS; if there are communication errors before, the usual MHD | ||
1471 | * connection error handling code will be performed. | ||
1472 | * | ||
1473 | * Setting the correct HTTP code (i.e. MHD_HTTP_SWITCHING_PROTOCOLS) | ||
1474 | * and setting correct HTTP headers for the upgrade must be done | ||
1475 | * manually (this way, it is possible to implement most existing | ||
1476 | * WebSocket versions using this API; in fact, this API might be useful | ||
1477 | * for any protocol switch, not just WebSockets). Note that | ||
1478 | * draft-ietf-hybi-thewebsocketprotocol-00 cannot be implemented this | ||
1479 | * way as the header "HTTP/1.1 101 WebSocket Protocol Handshake" | ||
1480 | * cannot be generated; instead, MHD will always produce "HTTP/1.1 101 | ||
1481 | * Switching Protocols" (if the response code 101 is used). | ||
1482 | * | ||
1483 | * As usual, the response object can be extended with header | ||
1484 | * information and then be used any number of times (as long as the | ||
1485 | * header information is not connection-specific). | ||
1486 | * | ||
1487 | * @param upgrade_handler function to call with the "upgraded" socket | ||
1488 | * @param upgrade_handler_cls closure for @a upgrade_handler | ||
1489 | * @return NULL on error (i.e. invalid arguments, out of memory) | ||
1490 | */ | ||
1491 | _MHD_EXTERN struct MHD_Response * | ||
1492 | MHD_response_for_upgrade (MHD_UpgradeHandler upgrade_handler, | ||
1493 | void *upgrade_handler_cls); | ||
1494 | |||
1495 | |||
1496 | /** | ||
1497 | * Destroy a response object and associated resources. Note that | ||
1498 | * libmicrohttpd may keep some of the resources around if the response | ||
1499 | * is still in the queue for some clients, so the memory may not | ||
1500 | * necessarily be freed immediatley. | ||
1501 | * | ||
1502 | * @param response response to destroy | ||
1503 | * @ingroup response | ||
1504 | */ | ||
1505 | _MHD_EXTERN void | ||
1506 | MHD_response_destroy (struct MHD_Response *response); | ||
1507 | |||
1508 | |||
1509 | /** | ||
1510 | * Add a header line to the response. | ||
1511 | * | ||
1512 | * @param response response to add a header to | ||
1513 | * @param header the header to add | ||
1514 | * @param content value to add | ||
1515 | * @return #MHD_NO on error (i.e. invalid header or content format), | ||
1516 | * or out of memory | ||
1517 | * @ingroup response | ||
1518 | */ | ||
1519 | _MHD_EXTERN enum MHD_Bool | ||
1520 | MHD_response_add_header (struct MHD_Response *response, | ||
1521 | const char *header, | ||
1522 | const char *content); | ||
1523 | |||
1524 | |||
1525 | /** | ||
1526 | * Add a footer line to the response. | ||
1527 | * | ||
1528 | * @param response response to remove a header from | ||
1529 | * @param footer the footer to delete | ||
1530 | * @param content value to delete | ||
1531 | * @return #MHD_NO on error (i.e. invalid footer or content format). | ||
1532 | * @ingroup response | ||
1533 | */ | ||
1534 | _MHD_EXTERN enum MHD_Bool | ||
1535 | MHD_response_add_footer (struct MHD_Response *response, | ||
1536 | const char *footer, | ||
1537 | const char *content); | ||
1538 | |||
1539 | |||
1540 | /** | ||
1541 | * Delete a header (or footer) line from the response. | ||
1542 | * | ||
1543 | * @param response response to remove a header from | ||
1544 | * @param header the header to delete | ||
1545 | * @param content value to delete | ||
1546 | * @return #MHD_NO on error (no such header known) | ||
1547 | * @ingroup response | ||
1548 | */ | ||
1549 | _MHD_EXTERN enum MHD_Bool | ||
1550 | MHD_response_del_header (struct MHD_Response *response, | ||
1551 | const char *header, | ||
1552 | const char *content); | ||
1553 | |||
1554 | |||
1555 | /** | ||
1556 | * Get all of the headers (and footers) added to a response. | ||
1557 | * | ||
1558 | * @param response response to query | ||
1559 | * @param iterator callback to call on each header; | ||
1560 | * maybe NULL (then just count headers) | ||
1561 | * @param iterator_cls extra argument to @a iterator | ||
1562 | * @return number of entries iterated over | ||
1563 | * @ingroup response | ||
1564 | */ | ||
1565 | _MHD_EXTERN unsigned int | ||
1566 | MHD_response_get_headers (struct MHD_Response *response, | ||
1567 | MHD_KeyValueIterator iterator, | ||
1568 | void *iterator_cls); | ||
1569 | |||
1570 | |||
1571 | /** | ||
1572 | * Get a particular header (or footer) from the response. | ||
1573 | * | ||
1574 | * @param response response to query | ||
1575 | * @param key which header to get | ||
1576 | * @return NULL if header does not exist | ||
1577 | * @ingroup response | ||
1578 | */ | ||
1579 | _MHD_EXTERN const char * | ||
1580 | MHD_response_get_header (struct MHD_Response *response, | ||
1581 | const char *key); | ||
1582 | |||
1583 | |||
1584 | /* ********************** PostProcessor functions ********************** */ | ||
1585 | |||
1586 | /** | ||
1587 | * Create a `struct MHD_PostProcessor`. | ||
1588 | * | ||
1589 | * A `struct MHD_PostProcessor` can be used to (incrementally) parse | ||
1590 | * the data portion of a POST request. Note that some buggy browsers | ||
1591 | * fail to set the encoding type. If you want to support those, you | ||
1592 | * may have to call #MHD_set_connection_value with the proper encoding | ||
1593 | * type before creating a post processor (if no supported encoding | ||
1594 | * type is set, this function will fail). | ||
1595 | * | ||
1596 | * @param connection the connection on which the POST is | ||
1597 | * happening (used to determine the POST format) | ||
1598 | * @param buffer_size maximum number of bytes to use for | ||
1599 | * internal buffering (used only for the parsing, | ||
1600 | * specifically the parsing of the keys). A | ||
1601 | * tiny value (256-1024) should be sufficient. | ||
1602 | * Do NOT use a value smaller than 256. For good | ||
1603 | * performance, use 32 or 64k (i.e. 65536). | ||
1604 | * @param iter iterator to be called with the parsed data, | ||
1605 | * Must NOT be NULL. | ||
1606 | * @param iter_cls first argument to @a iter | ||
1607 | * @return NULL on error (out of memory, unsupported encoding), | ||
1608 | * otherwise a PP handle | ||
1609 | * @ingroup request | ||
1610 | */ | ||
1611 | _MHD_EXTERN struct MHD_PostProcessor * | ||
1612 | MHD_post_processor_create (struct MHD_Connection *connection, | ||
1613 | size_t buffer_size, | ||
1614 | MHD_PostDataIterator iter, | ||
1615 | void *iter_cls); | ||
1616 | |||
1617 | |||
1618 | /** | ||
1619 | * Parse and process POST data. Call this function when POST data is | ||
1620 | * available (usually during an #MHD_AccessHandlerCallback) with the | ||
1621 | * "upload_data" and "upload_data_size". Whenever possible, this will | ||
1622 | * then cause calls to the #MHD_PostDataIterator. | ||
1623 | * | ||
1624 | * @param pp the post processor | ||
1625 | * @param post_data @a post_data_len bytes of POST data | ||
1626 | * @param post_data_len length of @a post_data | ||
1627 | * @return #MHD_YES on success, #MHD_NO on error | ||
1628 | * (out-of-memory, iterator aborted, parse error) | ||
1629 | * @ingroup request | ||
1630 | */ | ||
1631 | _MHD_EXTERN enum MHD_Bool | ||
1632 | MHD_post_processor_run (struct MHD_PostProcessor *pp, | ||
1633 | const char *post_data, | ||
1634 | size_t post_data_len); | ||
1635 | |||
1636 | |||
1637 | /** | ||
1638 | * Release PostProcessor resources. | ||
1639 | * | ||
1640 | * @param pp the PostProcessor to destroy | ||
1641 | * @return #MHD_YES if processing completed nicely, | ||
1642 | * #MHD_NO if there were spurious characters / formatting | ||
1643 | * problems; it is common to ignore the return | ||
1644 | * value of this function | ||
1645 | * @ingroup request | ||
1646 | */ | ||
1647 | _MHD_EXTERN enum MHD_Bool | ||
1648 | MHD_post_processor_destroy (struct MHD_PostProcessor *pp); | ||
1649 | |||
1650 | |||
1651 | /* ********************** generic query functions ********************** */ | ||
1652 | |||
1653 | |||
1654 | /** | ||
1655 | * Select which member of the `struct ConnectionInformation` | ||
1656 | * union is desired to be returned by #MHD_connection_get_info(). | ||
1657 | */ | ||
1658 | enum MHD_ConnectionInformationType | ||
1659 | { | ||
1660 | /** | ||
1661 | * What cipher algorithm is being used. | ||
1662 | * Takes no extra arguments. | ||
1663 | * @ingroup request | ||
1664 | */ | ||
1665 | MHD_CONNECTION_INFORMATION_CIPHER_ALGO, | ||
1666 | |||
1667 | /** | ||
1668 | * | ||
1669 | * Takes no extra arguments. | ||
1670 | * @ingroup request | ||
1671 | */ | ||
1672 | MHD_CONNECTION_INFORMATION_PROTOCOL, | ||
1673 | |||
1674 | /** | ||
1675 | * Obtain IP address of the client. Takes no extra arguments. | ||
1676 | * Returns essentially a `struct sockaddr **` (since the API returns | ||
1677 | * a `union MHD_ConnectionInfo *` and that union contains a `struct | ||
1678 | * sockaddr *`). | ||
1679 | * @ingroup request | ||
1680 | */ | ||
1681 | MHD_CONNECTION_INFORMATION_CLIENT_ADDRESS, | ||
1682 | |||
1683 | /** | ||
1684 | * Get the gnuTLS session handle. | ||
1685 | * @ingroup request | ||
1686 | */ | ||
1687 | MHD_CONNECTION_INFORMATION_GNUTLS_SESSION, | ||
1688 | |||
1689 | /** | ||
1690 | * Get the gnuTLS client certificate handle. Dysfunctional (never | ||
1691 | * implemented, deprecated). Use #MHD_CONNECTION_INFORMATION_GNUTLS_SESSION | ||
1692 | * to get the `gnutls_session_t` and then call | ||
1693 | * gnutls_certificate_get_peers(). | ||
1694 | */ | ||
1695 | MHD_CONNECTION_INFORMATION_GNUTLS_CLIENT_CERT, | ||
1696 | |||
1697 | /** | ||
1698 | * Get the `struct MHD_Daemon *` responsible for managing this connection. | ||
1699 | * @ingroup request | ||
1700 | */ | ||
1701 | MHD_CONNECTION_INFORMATION_DAEMON, | ||
1702 | |||
1703 | /** | ||
1704 | * Request the file descriptor for the connection socket. | ||
1705 | * No extra arguments should be passed. | ||
1706 | * @ingroup request | ||
1707 | */ | ||
1708 | MHD_CONNECTION_INFORMATION_CONNECTION_FD, | ||
1709 | |||
1710 | /** | ||
1711 | * Returns the client-specific pointer to a `void *` that was (possibly) | ||
1712 | * set during a #MHD_NotifyConnectionCallback when the socket was | ||
1713 | * first accepted. Note that this is NOT the same as the "con_cls" | ||
1714 | * argument of the #MHD_AccessHandlerCallback. The "con_cls" is | ||
1715 | * fresh for each HTTP request, while the "socket_context" is fresh | ||
1716 | * for each socket. | ||
1717 | */ | ||
1718 | MHD_CONNECTION_INFORMATION_SOCKET_CONTEXT, | ||
1719 | |||
1720 | /** | ||
1721 | * Get connection timeout | ||
1722 | * @ingroup request | ||
1723 | */ | ||
1724 | MHD_CONNECTION_INFORMATION_CONNECTION_TIMEOUT | ||
1725 | |||
1726 | }; | ||
1727 | |||
1728 | |||
1729 | /** | ||
1730 | * Information about a connection. | ||
1731 | */ | ||
1732 | union MHD_ConnectionInformation | ||
1733 | { | ||
1734 | |||
1735 | /** | ||
1736 | * Cipher algorithm used, of type "enum gnutls_cipher_algorithm". | ||
1737 | */ | ||
1738 | int /* enum gnutls_cipher_algorithm */ cipher_algorithm; | ||
1739 | |||
1740 | /** | ||
1741 | * Protocol used, of type "enum gnutls_protocol". | ||
1742 | */ | ||
1743 | int /* enum gnutls_protocol */ protocol; | ||
1744 | |||
1745 | /** | ||
1746 | * Amount of second that connection could spend in idle state | ||
1747 | * before automatically disconnected. | ||
1748 | * Zero for no timeout (unlimited idle time). | ||
1749 | */ | ||
1750 | unsigned int connection_timeout; | ||
1751 | |||
1752 | /** | ||
1753 | * Connect socket | ||
1754 | */ | ||
1755 | MHD_socket connect_fd; | ||
1756 | |||
1757 | /** | ||
1758 | * GNUtls session handle, of type "gnutls_session_t". | ||
1759 | */ | ||
1760 | void * /* gnutls_session_t */ tls_session; | ||
1761 | |||
1762 | /** | ||
1763 | * GNUtls client certificate handle, of type "gnutls_x509_crt_t". | ||
1764 | */ | ||
1765 | void * /* gnutls_x509_crt_t */ client_cert; | ||
1766 | |||
1767 | /** | ||
1768 | * Address information for the client. | ||
1769 | */ | ||
1770 | struct sockaddr *client_addr; | ||
1771 | |||
1772 | /** | ||
1773 | * Which daemon manages this connection (useful in case there are many | ||
1774 | * daemons running). | ||
1775 | */ | ||
1776 | struct MHD_Daemon *daemon; | ||
1777 | |||
1778 | /** | ||
1779 | * Socket-specific client context. Points to the same address as | ||
1780 | * the "socket_context" of the #MHD_NotifyConnectionCallback. | ||
1781 | */ | ||
1782 | void *socket_context; | ||
1783 | }; | ||
1784 | |||
1785 | |||
1786 | /** | ||
1787 | * Obtain information about the given connection. | ||
1788 | * | ||
1789 | * @param connection what connection to get information about | ||
1790 | * @param info_type what information is desired? | ||
1791 | * @param ... depends on @a info_type | ||
1792 | * @return NULL if this information is not available | ||
1793 | * (or if the @a info_type is unknown) | ||
1794 | * @ingroup specialized | ||
1795 | */ | ||
1796 | _MHD_EXTERN const union MHD_ConnectionInformation * | ||
1797 | MHD_connection_get_information (struct MHD_Connection *connection, | ||
1798 | enum MHD_ConnectionInformationType info_type, | ||
1799 | ...); | ||
1800 | |||
1801 | |||
1802 | /** | ||
1803 | * Information we return about a request. | ||
1804 | */ | ||
1805 | union MHD_RequestInformation | ||
1806 | { | ||
1807 | |||
1808 | /** | ||
1809 | * Connection via which we received the request. | ||
1810 | */ | ||
1811 | struct MHD_Connection *connection; | ||
1812 | |||
1813 | /** | ||
1814 | * The suspended status of a request. | ||
1815 | */ | ||
1816 | enum MHD_Bool suspended; | ||
1817 | |||
1818 | /** | ||
1819 | * HTTP version requested by the client. | ||
1820 | */ | ||
1821 | const char *http_version; | ||
1822 | |||
1823 | /** | ||
1824 | * Size of the client's HTTP header. | ||
1825 | */ | ||
1826 | size_t header_size; | ||
1827 | |||
1828 | }; | ||
1829 | |||
1830 | |||
1831 | /** | ||
1832 | * Select which member of the `struct RequestInformation` | ||
1833 | * union is desired to be returned by #MHD_request_get_info(). | ||
1834 | */ | ||
1835 | enum MHD_RequestInformationType | ||
1836 | { | ||
1837 | /** | ||
1838 | * Return which connection the request is associated with. | ||
1839 | */ | ||
1840 | MHD_REQUEST_INFORMATION_CONNECTION, | ||
1841 | |||
1842 | /** | ||
1843 | * Check whether the connection is suspended. | ||
1844 | * @ingroup request | ||
1845 | */ | ||
1846 | MHD_REQUEST_INFORMATION_SUSPENDED, | ||
1847 | |||
1848 | /** | ||
1849 | * Return the HTTP version string given by the client. | ||
1850 | * @ingroup request | ||
1851 | */ | ||
1852 | MHD_REQUEST_INFORMATION_HTTP_VERSION, | ||
1853 | |||
1854 | /** | ||
1855 | * Return length of the client's HTTP request header. | ||
1856 | * @ingroup request | ||
1857 | */ | ||
1858 | MHD_REQUEST_INFORMATION_HEADER_SIZE | ||
1859 | }; | ||
1860 | |||
1861 | |||
1862 | /** | ||
1863 | * Obtain information about the given connection. | ||
1864 | * | ||
1865 | * @param connection what connection to get information about | ||
1866 | * @param info_type what information is desired? | ||
1867 | * @param ... depends on @a info_type | ||
1868 | * @return NULL if this information is not available | ||
1869 | * (or if the @a info_type is unknown) | ||
1870 | * @ingroup specialized | ||
1871 | */ | ||
1872 | _MHD_EXTERN const union MHD_RequestInformation * | ||
1873 | MHD_request_get_information (struct MHD_Request *request, | ||
1874 | enum MHD_RequestInformationType info_type, | ||
1875 | ...); | ||
1876 | |||
1877 | |||
1878 | /** | ||
1879 | * Values of this enum are used to specify what | ||
1880 | * information about a deamon is desired. | ||
1881 | */ | ||
1882 | enum MHD_DaemonInformationType | ||
1883 | { | ||
1884 | |||
1885 | /** | ||
1886 | * Request the file descriptor for the listening socket. | ||
1887 | * No extra arguments should be passed. | ||
1888 | */ | ||
1889 | MHD_DAEMON_INFORMATION_LISTEN_FD, | ||
1890 | |||
1891 | /** | ||
1892 | * Request the file descriptor for the external epoll. | ||
1893 | * No extra arguments should be passed. | ||
1894 | */ | ||
1895 | MHD_DAEMON_INFORMATION_EPOLL_FD, | ||
1896 | |||
1897 | /** | ||
1898 | * Request the number of current connections handled by the daemon. | ||
1899 | * No extra arguments should be passed. | ||
1900 | * Note: when using MHD in external polling mode, this type of request | ||
1901 | * could be used only when #MHD_run()/#MHD_run_from_select is not | ||
1902 | * working in other thread at the same time. | ||
1903 | */ | ||
1904 | MHD_DAEMON_INFORMATION_CURRENT_CONNECTIONS, | ||
1905 | |||
1906 | /** | ||
1907 | * Request the port number of daemon's listen socket. | ||
1908 | * No extra arguments should be passed. | ||
1909 | * Note: if port '0' was specified for #MHD_option_port(), returned | ||
1910 | * value will be real port number. | ||
1911 | */ | ||
1912 | MHD_DAEMON_INFORMATION_BIND_PORT | ||
1913 | }; | ||
1914 | |||
1915 | |||
1916 | /** | ||
1917 | * Information about an MHD daemon. | ||
1918 | */ | ||
1919 | union MHD_DaemonInformation | ||
1920 | { | ||
1921 | |||
1922 | /** | ||
1923 | * Socket, returned for #MHD_DAEMON_INFORMATION_LISTEN_FD. | ||
1924 | */ | ||
1925 | MHD_socket listen_fd; | ||
1926 | |||
1927 | /** | ||
1928 | * Bind port number, returned for #MHD_DAEMON_INFORMATION_BIND_PORT. | ||
1929 | */ | ||
1930 | uint16_t port; | ||
1931 | |||
1932 | /** | ||
1933 | * epoll FD, returned for #MHD_DAEMON_INFORMATION_EPOLL_FD. | ||
1934 | */ | ||
1935 | int epoll_fd; | ||
1936 | |||
1937 | /** | ||
1938 | * Number of active connections, for #MHD_DAEMON_INFORMATION_CURRENT_CONNECTIONS. | ||
1939 | */ | ||
1940 | unsigned int num_connections; | ||
1941 | |||
1942 | }; | ||
1943 | |||
1944 | |||
1945 | /** | ||
1946 | * Obtain information about the given daemon | ||
1947 | * (not fully implemented!). | ||
1948 | * | ||
1949 | * @param daemon what daemon to get information about | ||
1950 | * @param info_type what information is desired? | ||
1951 | * @param ... depends on @a info_type | ||
1952 | * @return NULL if this information is not available | ||
1953 | * (or if the @a info_type is unknown) | ||
1954 | * @ingroup specialized | ||
1955 | */ | ||
1956 | _MHD_EXTERN const union MHD_DaemonInformation * | ||
1957 | MHD_daemon_get_information (struct MHD_Daemon *daemon, | ||
1958 | enum MHD_DaemonInformationType info_type, | ||
1959 | ...); | ||
1960 | |||