tolerate additional IPv4 address now available for gnunet.org
[oweals/gnunet.git] / src / transport / plugin_transport_http.h
1 /*
2      This file is part of GNUnet
3      Copyright (C) 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009 GNUnet e.V.
4
5      GNUnet is free software: you can redistribute it and/or modify it
6      under the terms of the GNU Affero General Public License as published
7      by the Free Software Foundation, either version 3 of the License,
8      or (at your option) any later version.
9
10      GNUnet is distributed in the hope that it will be useful, but
11      WITHOUT ANY WARRANTY; without even the implied warranty of
12      MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
13      Affero General Public License for more details.
14     
15      You should have received a copy of the GNU Affero General Public License
16      along with this program.  If not, see <http://www.gnu.org/licenses/>.
17
18      SPDX-License-Identifier: AGPL3.0-or-later
19 */
20
21 /**
22  * @file transport/plugin_transport_http.h
23  * @brief http transport service plugin
24  * @author Matthias Wachs
25  */
26 #ifndef PLUGIN_TRANSPORT_HTTP_H
27 #define PLUGIN_TRANSPORT_HTTP_H
28
29 #include "platform.h"
30 #include "gnunet_common.h"
31 #include "gnunet_constants.h"
32 #include "gnunet_protocols.h"
33 #include "gnunet_connection_lib.h"
34 #include "gnunet_service_lib.h"
35 #include "gnunet_statistics_service.h"
36 #include "gnunet_transport_service.h"
37 #include "gnunet_resolver_service.h"
38 #include "gnunet_server_lib.h"
39 #include "gnunet_container_lib.h"
40 #include "gnunet_transport_plugin.h"
41 #include "gnunet_os_lib.h"
42 #include "gnunet_nat_lib.h"
43 #include "microhttpd.h"
44 /* Just included for the right curl.h */
45 #include "gnunet_curl_lib.h"
46
47
48 #define DEBUG_HTTP GNUNET_EXTRA_LOGGING
49 #define VERBOSE_SERVER GNUNET_EXTRA_LOGGING
50 #define VERBOSE_CLIENT GNUNET_EXTRA_LOGGING
51 #define VERBOSE_CURL GNUNET_NO
52
53 #if BUILD_HTTPS
54 #define LIBGNUNET_PLUGIN_TRANSPORT_INIT libgnunet_plugin_transport_https_init
55 #define LIBGNUNET_PLUGIN_TRANSPORT_DONE libgnunet_plugin_transport_https_done
56 #else
57 #define LIBGNUNET_PLUGIN_TRANSPORT_INIT libgnunet_plugin_transport_http_init
58 #define LIBGNUNET_PLUGIN_TRANSPORT_DONE libgnunet_plugin_transport_http_done
59 #endif
60
61 #define INBOUND  GNUNET_YES
62 #define OUTBOUND GNUNET_NO
63
64
65 #define HTTP_NOT_VALIDATED_TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 15)
66
67 /**
68  * Encapsulation of all of the state of the plugin.
69  */
70 struct Plugin
71 {
72   /**
73    * Our environment.
74    */
75   struct GNUNET_TRANSPORT_PluginEnvironment *env;
76
77   /**
78    * Head of linked list of open sessions.
79    */
80   struct GNUNET_ATS_Session *head;
81
82   /**
83    * Tail of linked list of open sessions.
84    */
85   struct GNUNET_ATS_Session *tail;
86
87   /**
88    * NAT handle & address management
89    */
90   struct GNUNET_NAT_Handle *nat;
91
92   /**
93    * Our own IPv4 addresses DLL head
94    */
95   struct HttpAddressWrapper *addr_head;
96
97   /**
98    * Our own IPv4 addresses DLL tail
99    */
100   struct HttpAddressWrapper *addr_tail;
101
102   /**
103    * External hostname the plugin can be connected to, can be different to
104    * the host's FQDN, used e.g. for reverse proxying
105    */
106   char *external_hostname;
107
108   /**
109    * External hostname the plugin can be connected to, can be different to
110    * the host's FQDN, used e.g. for reverse proxying
111    */
112   struct HttpAddress *ext_addr;
113
114   /**
115    * External address length
116    */
117   size_t ext_addr_len;
118
119   /**
120    * Task calling transport service about external address
121    */
122   struct GNUNET_SCHEDULER_Task * notify_ext_task;
123
124   /**
125    * Plugin name.
126    * Equals configuration section: transport-http, transport-https
127    */
128   char *name;
129
130   /**
131    * Plugin protocol
132    * http, https
133    */
134   char *protocol;
135
136   /**
137    * Use IPv4? #GNUNET_YES or #GNUNET_NO
138    */
139   int ipv4;
140
141   /**
142    * Use IPv6? #GNUNET_YES or #GNUNET_NO
143    */
144   int ipv6;
145
146   /**
147    * Does plugin just use outbound connections and not accept inbound?
148    */
149   int client_only;
150
151   /**
152    * Port used
153    */
154   uint16_t port;
155
156   /**
157    * Maximum number of sockets the plugin can use
158    * Each http inbound /outbound connections are two connections
159    */
160   int max_connections;
161
162   /**
163    * Number of outbound sessions
164    */
165   unsigned int outbound_sessions;
166
167   /**
168    * Number of inbound sessions
169    */
170   unsigned int inbound_sessions;
171
172   /**
173    * libCurl TLS crypto init string, can be set to enhance performance
174    *
175    * Example:
176    *
177    * Use RC4-128 instead of AES:
178    * NONE:+VERS-TLS1.0:+ARCFOUR-128:+SHA1:+RSA:+COMP-NULL
179    */
180   char *crypto_init;
181
182   /**
183    * TLS key
184    */
185   char *key;
186
187   /**
188    * TLS certificate
189    */
190   char *cert;
191
192   /**
193    * Current number of establishes connections
194    */
195   int cur_connections;
196
197   /**
198    * Last used unique HTTP connection tag
199    */
200   uint32_t last_tag;
201
202   /**
203    * MHD IPv4 daemon
204    */
205   struct MHD_Daemon *server_v4;
206
207   /**
208    * MHD IPv4 task
209    */
210   struct GNUNET_SCHEDULER_Task * server_v4_task;
211
212   /**
213    * The IPv4 server is scheduled to run asap
214    */
215   int server_v4_immediately;
216
217   /**
218    * MHD IPv6 daemon
219    */
220   struct MHD_Daemon *server_v6;
221
222   /**
223    * MHD IPv4 task
224    */
225   struct GNUNET_SCHEDULER_Task * server_v6_task;
226
227   /**
228    * The IPv6 server is scheduled to run asap
229    */
230   int server_v6_immediately;
231
232   /**
233    * IPv4 server socket to bind to
234    */
235   struct sockaddr_in *server_addr_v4;
236
237   /**
238    * IPv6 server socket to bind to
239    */
240   struct sockaddr_in6 *server_addr_v6;
241
242   /**
243    * Head of server semi connections
244    * A full session consists of 2 semi-connections: send and receive
245    * If not both directions are established the server keeps this sessions here
246    */
247   struct GNUNET_ATS_Session *server_semi_head;
248
249   /**
250    * Tail of server semi connections
251    * A full session consists of 2 semi-connections: send and receive
252    * If not both directions are established the server keeps this sessions here
253    */
254   struct GNUNET_ATS_Session *server_semi_tail;
255
256   /**
257    * cURL Multihandle
258    */
259   CURLM *client_mh;
260
261   /**
262    * curl perform task
263    */
264   struct GNUNET_SCHEDULER_Task * client_perform_task;
265
266 };
267
268 GNUNET_NETWORK_STRUCT_BEGIN
269
270 /**
271  * HTTP addresses including a full URI
272  */
273 struct HttpAddress
274 {
275   /**
276    * Length of the address following in NBO
277    */
278   uint32_t addr_len GNUNET_PACKED;
279
280   /**
281    * Address following
282    */
283   void *addr GNUNET_PACKED;
284 };
285
286 /**
287  * IPv4 addresses
288  */
289 struct IPv4HttpAddress
290 {
291   /**
292    * IPv4 address, in network byte order.
293    */
294   uint32_t ipv4_addr GNUNET_PACKED;
295
296   /**
297    * Port number, in network byte order.
298    */
299   uint16_t u4_port GNUNET_PACKED;
300 };
301
302 /**
303  * IPv4 addresses
304  */
305 struct IPv6HttpAddress
306 {
307   /**
308    * IPv6 address.
309    */
310   struct in6_addr ipv6_addr GNUNET_PACKED;
311
312   /**
313    * Port number, in network byte order.
314    */
315   uint16_t u6_port GNUNET_PACKED;
316 };
317 GNUNET_NETWORK_STRUCT_END
318
319
320 struct ServerRequest
321 {
322   /**
323    * _RECV or _SEND
324    */
325   int direction;
326
327   /**
328    * Should this connection get disconnected? #GNUNET_YES / #GNUNET_NO
329    */
330   int disconnect;
331
332   /**
333    * The session this server connection belongs to
334    */
335   struct GNUNET_ATS_Session *session;
336
337   /**
338    * The MHD connection
339    */
340   struct MHD_Connection *mhd_conn;
341 };
342
343
344 /**
345  * Session handle for connections.
346  */
347 struct GNUNET_ATS_Session
348 {
349   /**
350    * To whom are we talking to
351    */
352   struct GNUNET_PeerIdentity target;
353
354   /**
355    * Stored in a linked list.
356    */
357   struct GNUNET_ATS_Session *next;
358
359   /**
360    * Stored in a linked list.
361    */
362   struct GNUNET_ATS_Session *prev;
363
364   /**
365    * Pointer to the global plugin struct.
366    */
367   struct Plugin *plugin;
368
369   /**
370    * Address
371    */
372   void *addr;
373
374   /**
375    * Address length
376    */
377   size_t addrlen;
378
379   /**
380    * ATS network type in NBO
381    */
382   uint32_t ats_address_network_type;
383
384   /**
385    * next pointer for double linked list
386    */
387   struct HTTP_Message *msg_head;
388
389   /**
390    * previous pointer for double linked list
391    */
392   struct HTTP_Message *msg_tail;
393
394   /**
395    * Message stream tokenizer for incoming data
396    */
397   struct GNUNET_SERVER_MessageStreamTokenizer *msg_tk;
398
399   /**
400    * Absolute time when to receive data again
401    * Used for receive throttling
402    */
403   struct GNUNET_TIME_Absolute next_receive;
404
405   /**
406    * Inbound or outbound connection
407    * Outbound: #GNUNET_NO (client is used to send and receive)
408    * Inbound : #GNUNET_YES (server is used to send and receive)
409    */
410   int inbound;
411
412   /**
413    * Unique HTTP/S connection tag for this connection
414    */
415   uint32_t tag;
416
417   /**
418    * Client send handle
419    */
420   void *client_put;
421
422   /**
423    * Client receive handle
424    */
425   void *client_get;
426
427   /**
428    * Task to wake up client receive handle when receiving is allowed again
429    */
430   struct GNUNET_SCHEDULER_Task * recv_wakeup_task;
431
432   /**
433    * Session timeout task
434    */
435   struct GNUNET_SCHEDULER_Task * timeout_task;
436
437   /**
438    * Is client send handle paused since there are no data to send?
439    * #GNUNET_YES or #GNUNET_NO
440    */
441   int client_put_paused;
442
443   /**
444    * Client send handle
445    */
446   struct ServerRequest *server_recv;
447
448   /**
449    * Client send handle
450    */
451   struct ServerRequest *server_send;
452 };
453
454
455 /**
456  *  Message to send using http
457  */
458 struct HTTP_Message
459 {
460   /**
461    * next pointer for double linked list
462    */
463   struct HTTP_Message *next;
464
465   /**
466    * previous pointer for double linked list
467    */
468   struct HTTP_Message *prev;
469
470   /**
471    * buffer containing data to send
472    */
473   char *buf;
474
475   /**
476    * amount of data already sent
477    */
478   size_t pos;
479
480   /**
481    * buffer length
482    */
483   size_t size;
484
485   /**
486    * Continuation function to call once the transmission buffer
487    * has again space available.  NULL if there is no
488    * continuation to call.
489    */
490   GNUNET_TRANSPORT_TransmitContinuation transmit_cont;
491
492   /**
493    * Closure for @e transmit_cont.
494    */
495   void *transmit_cont_cls;
496 };
497
498
499 struct GNUNET_ATS_Session *
500 create_session (struct Plugin *plugin,
501                 const struct GNUNET_PeerIdentity *target,
502                 const void *addr,
503                 size_t addrlen);
504
505
506 int
507 exist_session (struct Plugin *plugin,
508                struct GNUNET_ATS_Session *s);
509
510
511 void
512 delete_session (struct GNUNET_ATS_Session *s);
513
514
515 int
516 exist_session (struct Plugin *plugin,
517                struct GNUNET_ATS_Session *s);
518
519
520 struct GNUNET_TIME_Relative
521 http_plugin_receive (void *cls,
522                      const struct GNUNET_PeerIdentity *peer,
523                      const struct GNUNET_MessageHeader *message,
524                      struct GNUNET_ATS_Session *session,
525                      const char *sender_address,
526                      uint16_t sender_address_len);
527
528
529 const char *
530 http_plugin_address_to_string (void *cls,
531                                const void *addr,
532                                size_t addrlen);
533
534
535 int
536 client_disconnect (struct GNUNET_ATS_Session *s);
537
538
539 int
540 client_connect (struct GNUNET_ATS_Session *s);
541
542
543 int
544 client_send (struct GNUNET_ATS_Session *s, struct HTTP_Message *msg);
545
546
547 int
548 client_start (struct Plugin *plugin);
549
550
551 void
552 client_stop (struct Plugin *plugin);
553
554
555 int
556 server_disconnect (struct GNUNET_ATS_Session *s);
557
558
559 int
560 server_send (struct GNUNET_ATS_Session *s, struct HTTP_Message *msg);
561
562
563 int
564 server_start (struct Plugin *plugin);
565
566
567 void
568 server_stop (struct Plugin *plugin);
569
570
571 void
572 notify_session_end (void *cls,
573                     const struct GNUNET_PeerIdentity *peer,
574                     struct GNUNET_ATS_Session *s);
575
576
577 /*#ifndef PLUGIN_TRANSPORT_HTTP_H*/
578 #endif
579 /* end of plugin_transport_http.h */