aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorChristian Grothoff <christian@grothoff.org>2014-11-22 20:07:46 +0000
committerChristian Grothoff <christian@grothoff.org>2014-11-22 20:07:46 +0000
commit3a628a8b12195e3d15dce032d2e11110a6bb71a0 (patch)
treee04c545488b6e191f739b5bec4e1b6cc5db70e27 /src
parentdc82ebded4c48483815fd73d4e33750b73fed496 (diff)
downloadgnunet-3a628a8b12195e3d15dce032d2e11110a6bb71a0.tar.gz
gnunet-3a628a8b12195e3d15dce032d2e11110a6bb71a0.zip
adding TCP STEALTH support to HTTP client (without integrity protection)
Diffstat (limited to 'src')
-rw-r--r--src/transport/plugin_transport_http.h140
-rw-r--r--src/transport/plugin_transport_http_client.c449
-rw-r--r--src/transport/plugin_transport_http_common.h10
3 files changed, 408 insertions, 191 deletions
diff --git a/src/transport/plugin_transport_http.h b/src/transport/plugin_transport_http.h
index ae0c784ee..d43eb9bab 100644
--- a/src/transport/plugin_transport_http.h
+++ b/src/transport/plugin_transport_http.h
@@ -69,21 +69,18 @@
69struct Plugin 69struct Plugin
70{ 70{
71 /** 71 /**
72 * General handles
73 * ---------------
74 */
75
76 /**
77 * Our environment. 72 * Our environment.
78 */ 73 */
79 struct GNUNET_TRANSPORT_PluginEnvironment *env; 74 struct GNUNET_TRANSPORT_PluginEnvironment *env;
80 75
81 /** 76 /**
82 * Linked list of open sessions. 77 * Head of linked list of open sessions.
83 */ 78 */
84
85 struct Session *head; 79 struct Session *head;
86 80
81 /**
82 * Tail of linked list of open sessions.
83 */
87 struct Session *tail; 84 struct Session *tail;
88 85
89 /** 86 /**
@@ -92,25 +89,15 @@ struct Plugin
92 struct GNUNET_NAT_Handle *nat; 89 struct GNUNET_NAT_Handle *nat;
93 90
94 /** 91 /**
95 * List of own addresses 92 * Our own IPv4 addresses DLL head
96 */
97
98 /**
99 * IPv4 addresses DLL head
100 */ 93 */
101 struct HttpAddressWrapper *addr_head; 94 struct HttpAddressWrapper *addr_head;
102 95
103 /** 96 /**
104 * IPv4 addresses DLL tail 97 * Our own IPv4 addresses DLL tail
105 */ 98 */
106 struct HttpAddressWrapper *addr_tail; 99 struct HttpAddressWrapper *addr_tail;
107 100
108
109 /**
110 * Plugin configuration
111 * --------------------
112 */
113
114 /** 101 /**
115 * External hostname the plugin can be connected to, can be different to 102 * External hostname the plugin can be connected to, can be different to
116 * the host's FQDN, used e.g. for reverse proxying 103 * the host's FQDN, used e.g. for reverse proxying
@@ -133,9 +120,8 @@ struct Plugin
133 */ 120 */
134 GNUNET_SCHEDULER_TaskIdentifier notify_ext_task; 121 GNUNET_SCHEDULER_TaskIdentifier notify_ext_task;
135 122
136
137 /** 123 /**
138 * Plugin name 124 * Plugin name.
139 * Equals configuration section: transport-http, transport-https 125 * Equals configuration section: transport-http, transport-https
140 */ 126 */
141 char *name; 127 char *name;
@@ -147,21 +133,18 @@ struct Plugin
147 char *protocol; 133 char *protocol;
148 134
149 /** 135 /**
150 * Use IPv4? 136 * Use IPv4? #GNUNET_YES or #GNUNET_NO
151 * GNUNET_YES or GNUNET_NO
152 */ 137 */
153 int ipv4; 138 int ipv4;
154 139
155 /** 140 /**
156 * Use IPv6? 141 * Use IPv6? #GNUNET_YES or #GNUNET_NO
157 * GNUNET_YES or GNUNET_NO
158 */ 142 */
159 int ipv6; 143 int ipv6;
160 144
161 /** 145 /**
162 * Does plugin just use outbound connections and not accept inbound? 146 * Does plugin just use outbound connections and not accept inbound?
163 */ 147 */
164
165 int client_only; 148 int client_only;
166 149
167 /** 150 /**
@@ -186,18 +169,12 @@ struct Plugin
186 unsigned int inbound_sessions; 169 unsigned int inbound_sessions;
187 170
188 /** 171 /**
189 * Plugin HTTPS SSL/TLS options
190 * ----------------------------
191 */
192
193 /**
194 * libCurl TLS crypto init string, can be set to enhance performance 172 * libCurl TLS crypto init string, can be set to enhance performance
195 * 173 *
196 * Example: 174 * Example:
197 * 175 *
198 * Use RC4-128 instead of AES: 176 * Use RC4-128 instead of AES:
199 * NONE:+VERS-TLS1.0:+ARCFOUR-128:+SHA1:+RSA:+COMP-NULL 177 * NONE:+VERS-TLS1.0:+ARCFOUR-128:+SHA1:+RSA:+COMP-NULL
200 *
201 */ 178 */
202 char *crypto_init; 179 char *crypto_init;
203 180
@@ -212,11 +189,6 @@ struct Plugin
212 char *cert; 189 char *cert;
213 190
214 /** 191 /**
215 * Plugin values
216 * -------------
217 */
218
219 /**
220 * Current number of establishes connections 192 * Current number of establishes connections
221 */ 193 */
222 int cur_connections; 194 int cur_connections;
@@ -227,11 +199,6 @@ struct Plugin
227 uint32_t last_tag; 199 uint32_t last_tag;
228 200
229 /** 201 /**
230 * Server handles
231 * --------------
232 */
233
234 /**
235 * MHD IPv4 daemon 202 * MHD IPv4 daemon
236 */ 203 */
237 struct MHD_Daemon *server_v4; 204 struct MHD_Daemon *server_v4;
@@ -259,7 +226,6 @@ struct Plugin
259 /** 226 /**
260 * The IPv6 server is scheduled to run asap 227 * The IPv6 server is scheduled to run asap
261 */ 228 */
262
263 int server_v6_immediately; 229 int server_v6_immediately;
264 230
265 /** 231 /**
@@ -273,17 +239,18 @@ struct Plugin
273 struct sockaddr_in6 *server_addr_v6; 239 struct sockaddr_in6 *server_addr_v6;
274 240
275 /** 241 /**
276 * Server semi connections 242 * Head of server semi connections
277 * A full session consists of 2 semi-connections: send and receive 243 * A full session consists of 2 semi-connections: send and receive
278 * If not both directions are established the server keeps this sessions here 244 * If not both directions are established the server keeps this sessions here
279 */ 245 */
280 struct Session *server_semi_head; 246 struct Session *server_semi_head;
281 247
282 struct Session *server_semi_tail; 248 /**
283 249 * Tail of server semi connections
284 /* 250 * A full session consists of 2 semi-connections: send and receive
285 * Client handles 251 * If not both directions are established the server keeps this sessions here
286 */ 252 */
253 struct Session *server_semi_tail;
287 254
288 /** 255 /**
289 * cURL Multihandle 256 * cURL Multihandle
@@ -351,21 +318,28 @@ GNUNET_NETWORK_STRUCT_END
351 318
352struct ServerRequest 319struct ServerRequest
353{ 320{
354 /* _RECV or _SEND */ 321 /**
322 * _RECV or _SEND
323 */
355 int direction; 324 int direction;
356 325
357 /* Should this connection get disconnected? GNUNET_YES/NO */ 326 /**
327 * Should this connection get disconnected? #GNUNET_YES / #GNUNET_NO
328 */
358 int disconnect; 329 int disconnect;
359 330
360 /* The session this server connection belongs to */ 331 /**
332 * The session this server connection belongs to
333 */
361 struct Session *session; 334 struct Session *session;
362 335
363 /* The MHD connection */ 336 /**
337 * The MHD connection
338 */
364 struct MHD_Connection *mhd_conn; 339 struct MHD_Connection *mhd_conn;
365}; 340};
366 341
367 342
368
369/** 343/**
370 * Session handle for connections. 344 * Session handle for connections.
371 */ 345 */
@@ -416,7 +390,6 @@ struct Session
416 */ 390 */
417 struct HTTP_Message *msg_tail; 391 struct HTTP_Message *msg_tail;
418 392
419
420 /** 393 /**
421 * Message stream tokenizer for incoming data 394 * Message stream tokenizer for incoming data
422 */ 395 */
@@ -430,8 +403,8 @@ struct Session
430 403
431 /** 404 /**
432 * Inbound or outbound connection 405 * Inbound or outbound connection
433 * Outbound: GNUNET_NO (client is used to send and receive) 406 * Outbound: #GNUNET_NO (client is used to send and receive)
434 * Inbound : GNUNET_YES (server is used to send and receive) 407 * Inbound : #GNUNET_YES (server is used to send and receive)
435 */ 408 */
436 int inbound; 409 int inbound;
437 410
@@ -441,10 +414,6 @@ struct Session
441 uint32_t tag; 414 uint32_t tag;
442 415
443 /** 416 /**
444 * Client handles
445 */
446
447 /**
448 * Client send handle 417 * Client send handle
449 */ 418 */
450 void *client_put; 419 void *client_put;
@@ -466,15 +435,11 @@ struct Session
466 435
467 /** 436 /**
468 * Is client send handle paused since there are no data to send? 437 * Is client send handle paused since there are no data to send?
469 * GNUNET_YES/NO 438 * #GNUNET_YES or #GNUNET_NO
470 */ 439 */
471 int client_put_paused; 440 int client_put_paused;
472 441
473 /** 442 /**
474 * Server handles
475 */
476
477 /**
478 * Client send handle 443 * Client send handle
479 */ 444 */
480 struct ServerRequest *server_recv; 445 struct ServerRequest *server_recv;
@@ -485,6 +450,7 @@ struct Session
485 struct ServerRequest *server_send; 450 struct ServerRequest *server_send;
486}; 451};
487 452
453
488/** 454/**
489 * Message to send using http 455 * Message to send using http
490 */ 456 */
@@ -523,64 +489,90 @@ struct HTTP_Message
523 GNUNET_TRANSPORT_TransmitContinuation transmit_cont; 489 GNUNET_TRANSPORT_TransmitContinuation transmit_cont;
524 490
525 /** 491 /**
526 * Closure for transmit_cont. 492 * Closure for @e transmit_cont.
527 */ 493 */
528 void *transmit_cont_cls; 494 void *transmit_cont_cls;
529}; 495};
530 496
497
531struct Session * 498struct Session *
532create_session (struct Plugin *plugin, const struct GNUNET_PeerIdentity *target, 499create_session (struct Plugin *plugin,
533 const void *addr, size_t addrlen); 500 const struct GNUNET_PeerIdentity *target,
501 const void *addr,
502 size_t addrlen);
503
534 504
535int 505int
536exist_session (struct Plugin *plugin, struct Session *s); 506exist_session (struct Plugin *plugin,
507 struct Session *s);
508
537 509
538void 510void
539delete_session (struct Session *s); 511delete_session (struct Session *s);
540 512
513
541int 514int
542exist_session (struct Plugin *plugin, struct Session *s); 515exist_session (struct Plugin *plugin,
516 struct Session *s);
517
543 518
544struct GNUNET_TIME_Relative 519struct GNUNET_TIME_Relative
545http_plugin_receive (void *cls, const struct GNUNET_PeerIdentity *peer, 520http_plugin_receive (void *cls,
521 const struct GNUNET_PeerIdentity *peer,
546 const struct GNUNET_MessageHeader *message, 522 const struct GNUNET_MessageHeader *message,
547 struct Session *session, const char *sender_address, 523 struct Session *session,
524 const char *sender_address,
548 uint16_t sender_address_len); 525 uint16_t sender_address_len);
549 526
527
550const char * 528const char *
551http_plugin_address_to_string (void *cls, const void *addr, size_t addrlen); 529http_plugin_address_to_string (void *cls,
530 const void *addr,
531 size_t addrlen);
532
552 533
553int 534int
554client_disconnect (struct Session *s); 535client_disconnect (struct Session *s);
555 536
537
556int 538int
557client_connect (struct Session *s); 539client_connect (struct Session *s);
558 540
541
559int 542int
560client_send (struct Session *s, struct HTTP_Message *msg); 543client_send (struct Session *s, struct HTTP_Message *msg);
561 544
545
562int 546int
563client_start (struct Plugin *plugin); 547client_start (struct Plugin *plugin);
564 548
549
565void 550void
566client_stop (struct Plugin *plugin); 551client_stop (struct Plugin *plugin);
567 552
553
568int 554int
569server_disconnect (struct Session *s); 555server_disconnect (struct Session *s);
570 556
557
571int 558int
572server_send (struct Session *s, struct HTTP_Message *msg); 559server_send (struct Session *s, struct HTTP_Message *msg);
573 560
561
574int 562int
575server_start (struct Plugin *plugin); 563server_start (struct Plugin *plugin);
576 564
565
577void 566void
578server_stop (struct Plugin *plugin); 567server_stop (struct Plugin *plugin);
579 568
569
580void 570void
581notify_session_end (void *cls, const struct GNUNET_PeerIdentity *peer, 571notify_session_end (void *cls,
572 const struct GNUNET_PeerIdentity *peer,
582 struct Session *s); 573 struct Session *s);
583 574
575
584/*#ifndef PLUGIN_TRANSPORT_HTTP_H*/ 576/*#ifndef PLUGIN_TRANSPORT_HTTP_H*/
585#endif 577#endif
586/* end of plugin_transport_http.h */ 578/* end of plugin_transport_http.h */
diff --git a/src/transport/plugin_transport_http_client.c b/src/transport/plugin_transport_http_client.c
index adb83c719..971e581fd 100644
--- a/src/transport/plugin_transport_http_client.c
+++ b/src/transport/plugin_transport_http_client.c
@@ -384,6 +384,7 @@ struct HTTP_Client_Plugin
384 int emulate_xhr; 384 int emulate_xhr;
385}; 385};
386 386
387
387/** 388/**
388 * Disconnect a session 389 * Disconnect a session
389 * 390 *
@@ -394,6 +395,7 @@ struct HTTP_Client_Plugin
394static int 395static int
395http_client_plugin_session_disconnect (void *cls, struct Session *s); 396http_client_plugin_session_disconnect (void *cls, struct Session *s);
396 397
398
397/** 399/**
398 * If a session monitor is attached, notify it about the new 400 * If a session monitor is attached, notify it about the new
399 * session state. 401 * session state.
@@ -589,20 +591,23 @@ client_schedule (struct HTTP_Client_Plugin *plugin,
589 mret = curl_multi_fdset (plugin->curl_multi_handle, &rs, &ws, &es, &max); 591 mret = curl_multi_fdset (plugin->curl_multi_handle, &rs, &ws, &es, &max);
590 if (mret != CURLM_OK) 592 if (mret != CURLM_OK)
591 { 593 {
592 LOG (GNUNET_ERROR_TYPE_ERROR, _("%s failed at %s:%d: `%s'\n"), 594 LOG (GNUNET_ERROR_TYPE_ERROR,
593 "curl_multi_fdset", __FILE__, __LINE__, 595 _("%s failed at %s:%d: `%s'\n"),
594 curl_multi_strerror (mret)); 596 "curl_multi_fdset",
597 __FILE__,
598 __LINE__,
599 curl_multi_strerror (mret));
595 return GNUNET_SYSERR; 600 return GNUNET_SYSERR;
596 } 601 }
597 mret = curl_multi_timeout (plugin->curl_multi_handle, &to); 602 mret = curl_multi_timeout (plugin->curl_multi_handle, &to);
598 if (to == -1) 603 if (-1 == to)
599 timeout = GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 1); 604 timeout = GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 1);
600 else 605 else
601 timeout = GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MILLISECONDS, to); 606 timeout = GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MILLISECONDS, to);
602 if (now == GNUNET_YES) 607 if (now == GNUNET_YES)
603 timeout = GNUNET_TIME_UNIT_MILLISECONDS; 608 timeout = GNUNET_TIME_UNIT_MILLISECONDS;
604 609
605 if (mret != CURLM_OK) 610 if (CURLM_OK != mret)
606 { 611 {
607 LOG (GNUNET_ERROR_TYPE_ERROR, 612 LOG (GNUNET_ERROR_TYPE_ERROR,
608 _("%s failed at %s:%d: `%s'\n"), 613 _("%s failed at %s:%d: `%s'\n"),
@@ -626,6 +631,7 @@ client_schedule (struct HTTP_Client_Plugin *plugin,
626 return GNUNET_OK; 631 return GNUNET_OK;
627} 632}
628 633
634
629#if VERBOSE_CURL 635#if VERBOSE_CURL
630/** 636/**
631 * Loggging function 637 * Loggging function
@@ -648,7 +654,9 @@ client_log (CURL *curl,
648 const char *ttype = "UNSPECIFIED"; 654 const char *ttype = "UNSPECIFIED";
649 char text[size + 2]; 655 char text[size + 2];
650 656
651 if (! ((type == CURLINFO_TEXT) || (type == CURLINFO_HEADER_IN) || (type == CURLINFO_HEADER_OUT))) 657 if (! ((CURLINFO_TEXT == type) ||
658 (CURLINFO_HEADER_IN == type) ||
659 (CURLINFO_HEADER_OUT == type)))
652 return 0; 660 return 0;
653 switch (type) 661 switch (type)
654 { 662 {
@@ -731,7 +739,7 @@ client_connect_put (struct Session *s);
731 * been transmitted (or if the transport is ready 739 * been transmitted (or if the transport is ready
732 * for the next transmission call; or if the 740 * for the next transmission call; or if the
733 * peer disconnected...); can be NULL 741 * peer disconnected...); can be NULL
734 * @param cont_cls closure for cont 742 * @param cont_cls closure for @a cont
735 * @return number of bytes used (on the physical network, with overheads); 743 * @return number of bytes used (on the physical network, with overheads);
736 * -1 on hard errors (i.e. address invalid); 0 is a legal value 744 * -1 on hard errors (i.e. address invalid); 0 is a legal value
737 * and does NOT mean that the message was not transmitted (DV) 745 * and does NOT mean that the message was not transmitted (DV)
@@ -752,18 +760,20 @@ http_client_plugin_send (void *cls,
752 760
753 LOG (GNUNET_ERROR_TYPE_DEBUG, 761 LOG (GNUNET_ERROR_TYPE_DEBUG,
754 "Session %p/request %p: Sending message with %u to peer `%s' \n", 762 "Session %p/request %p: Sending message with %u to peer `%s' \n",
755 s, s->put.easyhandle, 763 s,
756 msgbuf_size, GNUNET_i2s (&s->address->peer)); 764 s->put.easyhandle,
765 msgbuf_size,
766 GNUNET_i2s (&s->address->peer));
757 767
758 /* create new message and schedule */ 768 /* create new message and schedule */
759 msg = GNUNET_malloc (sizeof (struct HTTP_Message) + msgbuf_size); 769 msg = GNUNET_malloc (sizeof (struct HTTP_Message) + msgbuf_size);
760 msg->next = NULL;
761 msg->size = msgbuf_size; 770 msg->size = msgbuf_size;
762 msg->pos = 0;
763 msg->buf = (char *) &msg[1]; 771 msg->buf = (char *) &msg[1];
764 msg->transmit_cont = cont; 772 msg->transmit_cont = cont;
765 msg->transmit_cont_cls = cont_cls; 773 msg->transmit_cont_cls = cont_cls;
766 memcpy (msg->buf, msgbuf, msgbuf_size); 774 memcpy (msg->buf,
775 msgbuf,
776 msgbuf_size);
767 GNUNET_CONTAINER_DLL_insert_tail (s->msg_head, 777 GNUNET_CONTAINER_DLL_insert_tail (s->msg_head,
768 s->msg_tail, 778 s->msg_tail,
769 msg); 779 msg);
@@ -833,8 +843,11 @@ http_client_plugin_session_disconnect (void *cls,
833 struct HTTP_Client_Plugin *plugin = cls; 843 struct HTTP_Client_Plugin *plugin = cls;
834 844
835 LOG (GNUNET_ERROR_TYPE_DEBUG, 845 LOG (GNUNET_ERROR_TYPE_DEBUG,
836 "Session %p: notifying transport about ending session\n",s); 846 "Session %p: notifying transport about ending session\n",
837 plugin->env->session_end (plugin->env->cls, s->address, s); 847 s);
848 plugin->env->session_end (plugin->env->cls,
849 s->address,
850 s);
838 client_delete_session (s); 851 client_delete_session (s);
839 852
840 /* Re-schedule since handles have changed */ 853 /* Re-schedule since handles have changed */
@@ -902,8 +915,10 @@ http_client_plugin_peer_disconnect (void *cls,
902 LOG (GNUNET_ERROR_TYPE_DEBUG, 915 LOG (GNUNET_ERROR_TYPE_DEBUG,
903 "Transport tells me to disconnect `%s'\n", 916 "Transport tells me to disconnect `%s'\n",
904 GNUNET_i2s (target)); 917 GNUNET_i2s (target));
905 GNUNET_CONTAINER_multipeermap_get_multiple (plugin->sessions, target, 918 GNUNET_CONTAINER_multipeermap_get_multiple (plugin->sessions,
906 &destroy_session_cb, plugin); 919 target,
920 &destroy_session_cb,
921 plugin);
907} 922}
908 923
909 924
@@ -992,7 +1007,8 @@ client_put_disconnect (void *cls,
992 s, s->put.easyhandle); 1007 s, s->put.easyhandle);
993 s->put.state = H_TMP_DISCONNECTING; 1008 s->put.state = H_TMP_DISCONNECTING;
994 if (NULL != s->put.easyhandle) 1009 if (NULL != s->put.easyhandle)
995 curl_easy_pause (s->put.easyhandle, CURLPAUSE_CONT); 1010 curl_easy_pause (s->put.easyhandle,
1011 CURLPAUSE_CONT);
996 client_schedule (s->plugin, GNUNET_YES); 1012 client_schedule (s->plugin, GNUNET_YES);
997} 1013}
998 1014
@@ -1033,7 +1049,8 @@ client_send_cb (void *stream,
1033 { 1049 {
1034 LOG (GNUNET_ERROR_TYPE_DEBUG, 1050 LOG (GNUNET_ERROR_TYPE_DEBUG,
1035 "Session %p/request %p: PUT request finished\n", 1051 "Session %p/request %p: PUT request finished\n",
1036 s, s->put.easyhandle); 1052 s,
1053 s->put.easyhandle);
1037 s->put.state = H_TMP_DISCONNECTING; 1054 s->put.state = H_TMP_DISCONNECTING;
1038 return 0; 1055 return 0;
1039 } 1056 }
@@ -1041,7 +1058,8 @@ client_send_cb (void *stream,
1041 /* We have nothing to send, so pause PUT request */ 1058 /* We have nothing to send, so pause PUT request */
1042 LOG (GNUNET_ERROR_TYPE_DEBUG, 1059 LOG (GNUNET_ERROR_TYPE_DEBUG,
1043 "Session %p/request %p: nothing to send, suspending\n", 1060 "Session %p/request %p: nothing to send, suspending\n",
1044 s, s->put.easyhandle); 1061 s,
1062 s->put.easyhandle);
1045 s->put_disconnect_task = GNUNET_SCHEDULER_add_delayed (PUT_DISCONNECT_TIMEOUT, 1063 s->put_disconnect_task = GNUNET_SCHEDULER_add_delayed (PUT_DISCONNECT_TIMEOUT,
1046 &client_put_disconnect, s); 1064 &client_put_disconnect, s);
1047 s->put.state = H_PAUSED; 1065 s->put.state = H_PAUSED;
@@ -1058,7 +1076,10 @@ client_send_cb (void *stream,
1058 { 1076 {
1059 LOG (GNUNET_ERROR_TYPE_DEBUG, 1077 LOG (GNUNET_ERROR_TYPE_DEBUG,
1060 "Session %p/request %p: sent message with %u bytes sent, removing message from queue\n", 1078 "Session %p/request %p: sent message with %u bytes sent, removing message from queue\n",
1061 s, s->put.easyhandle, msg->size, msg->pos); 1079 s,
1080 s->put.easyhandle,
1081 msg->size,
1082 msg->pos);
1062 /* Calling transmit continuation */ 1083 /* Calling transmit continuation */
1063 GNUNET_CONTAINER_DLL_remove (s->msg_head, 1084 GNUNET_CONTAINER_DLL_remove (s->msg_head,
1064 s->msg_tail, 1085 s->msg_tail,
@@ -1161,7 +1182,8 @@ client_receive_mst_cb (void *cls,
1161 s, 1182 s,
1162 message); 1183 message);
1163 plugin->env->update_address_metrics (plugin->env->cls, 1184 plugin->env->update_address_metrics (plugin->env->cls,
1164 s->address, s, 1185 s->address,
1186 s,
1165 &atsi, 1); 1187 &atsi, 1);
1166 1188
1167 GNUNET_asprintf (&stat_txt, 1189 GNUNET_asprintf (&stat_txt,
@@ -1232,8 +1254,10 @@ client_receive (void *stream,
1232 1254
1233 LOG (GNUNET_ERROR_TYPE_DEBUG, 1255 LOG (GNUNET_ERROR_TYPE_DEBUG,
1234 "Session %p / request %p: Received %u bytes from peer `%s'\n", 1256 "Session %p / request %p: Received %u bytes from peer `%s'\n",
1235 s, s->get.easyhandle, 1257 s,
1236 len, GNUNET_i2s (&s->address->peer)); 1258 s->get.easyhandle,
1259 len,
1260 GNUNET_i2s (&s->address->peer));
1237 now = GNUNET_TIME_absolute_get (); 1261 now = GNUNET_TIME_absolute_get ();
1238 if (now.abs_value_us < s->next_receive.abs_value_us) 1262 if (now.abs_value_us < s->next_receive.abs_value_us)
1239 { 1263 {
@@ -1428,6 +1452,52 @@ client_run (void *cls,
1428} 1452}
1429 1453
1430 1454
1455#ifdef SO_TCPSTEALTH
1456/**
1457 * Open TCP socket with TCP STEALTH enabled.
1458 */
1459static curl_socket_t
1460open_tcp_stealth_socket_cb (void *clientp,
1461 curlsocktype purpose,
1462 struct curl_sockaddr *address)
1463{
1464 struct Session *s = clientp;
1465 int ret;
1466
1467 switch (purpose)
1468 {
1469 case CURLSOCKTYPE_IPCXN:
1470 ret = socket (address->family,
1471 address->socktype,
1472 address->protocol);
1473 if (-1 == ret)
1474 return CURL_SOCKET_BAD;
1475 if ( ( (SOCK_STREAM != address->socktype) ||
1476 ( (0 != address->protocol) &&
1477 (IPPROTO_TCP != address->protocol))) )
1478 return (curl_socket_t) ret;
1479 if ( (0 != setsockopt (ret,
1480 IPPROTO_TCP,
1481 SO_TCPSTEALTH,
1482 &s->target,
1483 sizeof (struct GNUNET_PeerIdentity))) )
1484 {
1485 (void) close (ret);
1486 return CURL_SOCKET_BAD;
1487 }
1488 return (curl_socket_t) ret;
1489 case CURLSOCKTYPE_ACCEPT:
1490 GNUNET_break (0);
1491 return CURL_SOCKET_BAD;
1492 break;
1493 case CURLSOCKTYPE_LAST:
1494 GNUNET_break (0);
1495 return CURL_SOCKET_BAD;
1496 }
1497}
1498#endif
1499
1500
1431/** 1501/**
1432 * Connect GET request for a session 1502 * Connect GET request for a session
1433 * 1503 *
@@ -1438,82 +1508,152 @@ static int
1438client_connect_get (struct Session *s) 1508client_connect_get (struct Session *s)
1439{ 1509{
1440 CURLMcode mret; 1510 CURLMcode mret;
1511 struct HttpAddress *ha;
1512 uint32_t options;
1441 1513
1514 ha = (struct HttpAddress *) s->address->address;
1515 options = ntohl (ha->options);
1442 /* create get request */ 1516 /* create get request */
1443 s->get.easyhandle = curl_easy_init (); 1517 s->get.easyhandle = curl_easy_init ();
1444 s->get.s = s; 1518 s->get.s = s;
1519 if (0 != (options & HTTP_OPTIONS_TCP_STEALTH))
1520 {
1521#ifdef SO_TCPSTEALTH
1522 curl_easy_setopt (s->get.easyhandle,
1523 CURLOPT_OPENSOCKETFUNCTION,
1524 &open_tcp_stealth_socket_cb);
1525 curl_easy_setopt (s->get.easyhandle,
1526 CURLOPT_OPENSOCKETDATA,
1527 s);
1528#else
1529 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
1530 "Cannot connect, TCP STEALTH needed and not supported by kernel.\n");
1531 curl_easy_cleanup (s->get.easyhandle);
1532 s->get.easyhandle = NULL;
1533 s->get.s = NULL;
1534 return GNUNET_SYSERR;
1535#endif
1536 }
1537
1445#if VERBOSE_CURL 1538#if VERBOSE_CURL
1446 curl_easy_setopt (s->get.easyhandle, CURLOPT_VERBOSE, 1L); 1539 curl_easy_setopt (s->get.easyhandle,
1447 curl_easy_setopt (s->get.easyhandle, CURLOPT_DEBUGFUNCTION, &client_log); 1540 CURLOPT_VERBOSE,
1448 curl_easy_setopt (s->get.easyhandle, CURLOPT_DEBUGDATA, &s->get); 1541 1L);
1542 curl_easy_setopt (s->get.easyhandle,
1543 CURLOPT_DEBUGFUNCTION,
1544 &client_log);
1545 curl_easy_setopt (s->get.easyhandle,
1546 CURLOPT_DEBUGDATA,
1547 &s->get);
1449#endif 1548#endif
1450#if BUILD_HTTPS 1549#if BUILD_HTTPS
1451 curl_easy_setopt (s->get.easyhandle, CURLOPT_SSLVERSION, CURL_SSLVERSION_TLSv1); 1550 curl_easy_setopt (s->get.easyhandle, CURLOPT_SSLVERSION, CURL_SSLVERSION_TLSv1);
1452 { 1551 {
1453 struct HttpAddress *ha;
1454
1455 ha = (struct HttpAddress *) s->address->address;
1456
1457 if (HTTP_OPTIONS_VERIFY_CERTIFICATE == 1552 if (HTTP_OPTIONS_VERIFY_CERTIFICATE ==
1458 (ntohl (ha->options) & HTTP_OPTIONS_VERIFY_CERTIFICATE)) 1553 (options & HTTP_OPTIONS_VERIFY_CERTIFICATE))
1459 { 1554 {
1460 curl_easy_setopt (s->get.easyhandle, CURLOPT_SSL_VERIFYPEER, 1L); 1555 curl_easy_setopt (s->get.easyhandle,
1461 curl_easy_setopt (s->get.easyhandle, CURLOPT_SSL_VERIFYHOST, 2L); 1556 CURLOPT_SSL_VERIFYPEER, 1L);
1557 curl_easy_setopt (s->get.easyhandle,
1558 CURLOPT_SSL_VERIFYHOST,
1559 2L);
1462 } 1560 }
1463 else 1561 else
1464 { 1562 {
1465 curl_easy_setopt (s->get.easyhandle, CURLOPT_SSL_VERIFYPEER, 0); 1563 curl_easy_setopt (s->get.easyhandle,
1466 curl_easy_setopt (s->get.easyhandle, CURLOPT_SSL_VERIFYHOST, 0); 1564 CURLOPT_SSL_VERIFYPEER,
1565 0L);
1566 curl_easy_setopt (s->get.easyhandle,
1567 CURLOPT_SSL_VERIFYHOST,
1568 0L);
1467 } 1569 }
1468 } 1570 }
1469 curl_easy_setopt (s->get.easyhandle, CURLOPT_PROTOCOLS, CURLPROTO_HTTPS); 1571 curl_easy_setopt (s->get.easyhandle,
1470 curl_easy_setopt (s->get.easyhandle, CURLOPT_REDIR_PROTOCOLS, CURLPROTO_HTTPS); 1572 CURLOPT_PROTOCOLS,
1573 CURLPROTO_HTTPS);
1574 curl_easy_setopt (s->get.easyhandle,
1575 CURLOPT_REDIR_PROTOCOLS,
1576 CURLPROTO_HTTPS);
1471#else 1577#else
1472 curl_easy_setopt (s->get.easyhandle, CURLOPT_PROTOCOLS, CURLPROTO_HTTP); 1578 curl_easy_setopt (s->get.easyhandle,
1473 curl_easy_setopt (s->get.easyhandle, CURLOPT_REDIR_PROTOCOLS, CURLPROTO_HTTP); 1579 CURLOPT_PROTOCOLS,
1580 CURLPROTO_HTTP);
1581 curl_easy_setopt (s->get.easyhandle,
1582 CURLOPT_REDIR_PROTOCOLS,
1583 CURLPROTO_HTTP);
1474#endif 1584#endif
1475 1585
1476 if (NULL != s->plugin->proxy_hostname) 1586 if (NULL != s->plugin->proxy_hostname)
1477 { 1587 {
1478 curl_easy_setopt (s->get.easyhandle, CURLOPT_PROXY, s->plugin->proxy_hostname); 1588 curl_easy_setopt (s->get.easyhandle,
1479 curl_easy_setopt (s->get.easyhandle, CURLOPT_PROXYTYPE, s->plugin->proxytype); 1589 CURLOPT_PROXY,
1590 s->plugin->proxy_hostname);
1591 curl_easy_setopt (s->get.easyhandle,
1592 CURLOPT_PROXYTYPE,
1593 s->plugin->proxytype);
1480 if (NULL != s->plugin->proxy_username) 1594 if (NULL != s->plugin->proxy_username)
1481 curl_easy_setopt (s->get.easyhandle, CURLOPT_PROXYUSERNAME, 1595 curl_easy_setopt (s->get.easyhandle,
1482 s->plugin->proxy_username); 1596 CURLOPT_PROXYUSERNAME,
1597 s->plugin->proxy_username);
1483 if (NULL != s->plugin->proxy_password) 1598 if (NULL != s->plugin->proxy_password)
1484 curl_easy_setopt (s->get.easyhandle, CURLOPT_PROXYPASSWORD, 1599 curl_easy_setopt (s->get.easyhandle,
1485 s->plugin->proxy_password); 1600 CURLOPT_PROXYPASSWORD,
1601 s->plugin->proxy_password);
1486 if (GNUNET_YES == s->plugin->proxy_use_httpproxytunnel) 1602 if (GNUNET_YES == s->plugin->proxy_use_httpproxytunnel)
1487 curl_easy_setopt (s->get.easyhandle, CURLOPT_HTTPPROXYTUNNEL, 1603 curl_easy_setopt (s->get.easyhandle,
1488 s->plugin->proxy_use_httpproxytunnel); 1604 CURLOPT_HTTPPROXYTUNNEL,
1605 s->plugin->proxy_use_httpproxytunnel);
1489 } 1606 }
1490 1607
1491 if (GNUNET_YES == s->plugin->emulate_xhr) 1608 if (GNUNET_YES == s->plugin->emulate_xhr)
1492 { 1609 {
1493 char *url; 1610 char *url;
1494 1611
1495 GNUNET_asprintf(&url, "%s,1", s->url); 1612 GNUNET_asprintf (&url,
1496 curl_easy_setopt (s->get.easyhandle, CURLOPT_URL, url); 1613 "%s,1",
1614 s->url);
1615 curl_easy_setopt (s->get.easyhandle,
1616 CURLOPT_URL,
1617 url);
1497 GNUNET_free(url); 1618 GNUNET_free(url);
1498 } else 1619 }
1499 curl_easy_setopt (s->get.easyhandle, CURLOPT_URL, s->url); 1620 else
1500 //curl_easy_setopt (s->get.easyhandle, CURLOPT_HEADERFUNCTION, &curl_get_header_cb); 1621 {
1501 //curl_easy_setopt (s->get.easyhandle, CURLOPT_WRITEHEADER, ps); 1622 curl_easy_setopt (s->get.easyhandle,
1502 curl_easy_setopt (s->get.easyhandle, CURLOPT_READFUNCTION, client_send_cb); 1623 CURLOPT_URL,
1503 curl_easy_setopt (s->get.easyhandle, CURLOPT_READDATA, s); 1624 s->url);
1504 curl_easy_setopt (s->get.easyhandle, CURLOPT_WRITEFUNCTION, client_receive); 1625 }
1505 curl_easy_setopt (s->get.easyhandle, CURLOPT_WRITEDATA, s); 1626 curl_easy_setopt (s->get.easyhandle,
1627 CURLOPT_READFUNCTION,
1628 &client_send_cb);
1629 curl_easy_setopt (s->get.easyhandle,
1630 CURLOPT_READDATA,
1631 s);
1632 curl_easy_setopt (s->get.easyhandle,
1633 CURLOPT_WRITEFUNCTION,
1634 &client_receive);
1635 curl_easy_setopt (s->get.easyhandle,
1636 CURLOPT_WRITEDATA,
1637 s);
1506 /* No timeout by default, timeout done with session timeout */ 1638 /* No timeout by default, timeout done with session timeout */
1507 curl_easy_setopt (s->get.easyhandle, CURLOPT_TIMEOUT, 0); 1639 curl_easy_setopt (s->get.easyhandle,
1508 curl_easy_setopt (s->get.easyhandle, CURLOPT_PRIVATE, s); 1640 CURLOPT_TIMEOUT,
1509 curl_easy_setopt (s->get.easyhandle, CURLOPT_CONNECTTIMEOUT_MS, 1641 0L);
1642 curl_easy_setopt (s->get.easyhandle,
1643 CURLOPT_PRIVATE, s);
1644 curl_easy_setopt (s->get.easyhandle,
1645 CURLOPT_CONNECTTIMEOUT_MS,
1510 (long) (HTTP_CLIENT_NOT_VALIDATED_TIMEOUT.rel_value_us / 1000LL)); 1646 (long) (HTTP_CLIENT_NOT_VALIDATED_TIMEOUT.rel_value_us / 1000LL));
1511 curl_easy_setopt (s->get.easyhandle, CURLOPT_BUFFERSIZE, 1647 curl_easy_setopt (s->get.easyhandle, CURLOPT_BUFFERSIZE,
1512 2 * GNUNET_SERVER_MAX_MESSAGE_SIZE); 1648 2 * GNUNET_SERVER_MAX_MESSAGE_SIZE);
1513#if CURL_TCP_NODELAY 1649#if CURL_TCP_NODELAY
1514 curl_easy_setopt (ps->recv_endpoint, CURLOPT_TCP_NODELAY, 1); 1650 curl_easy_setopt (ps->recv_endpoint,
1651 CURLOPT_TCP_NODELAY,
1652 1L);
1515#endif 1653#endif
1516 curl_easy_setopt (s->get.easyhandle, CURLOPT_FOLLOWLOCATION, 0); 1654 curl_easy_setopt (s->get.easyhandle,
1655 CURLOPT_FOLLOWLOCATION,
1656 0L);
1517 1657
1518 mret = curl_multi_add_handle (s->plugin->curl_multi_handle, 1658 mret = curl_multi_add_handle (s->plugin->curl_multi_handle,
1519 s->get.easyhandle); 1659 s->get.easyhandle);
@@ -1526,14 +1666,14 @@ client_connect_get (struct Session *s)
1526 curl_easy_cleanup (s->get.easyhandle); 1666 curl_easy_cleanup (s->get.easyhandle);
1527 s->get.easyhandle = NULL; 1667 s->get.easyhandle = NULL;
1528 s->get.s = NULL; 1668 s->get.s = NULL;
1529 s->get.easyhandle = NULL;
1530 GNUNET_break (0); 1669 GNUNET_break (0);
1531 return GNUNET_SYSERR; 1670 return GNUNET_SYSERR;
1532 } 1671 }
1533 s->plugin->cur_requests++; 1672 s->plugin->cur_requests++;
1534 LOG (GNUNET_ERROR_TYPE_INFO, 1673 LOG (GNUNET_ERROR_TYPE_INFO,
1535 "GET request `%s' established, number of requests increased to %u\n", 1674 "GET request `%s' established, number of requests increased to %u\n",
1536 s->url, s->plugin->cur_requests); 1675 s->url,
1676 s->plugin->cur_requests);
1537 return GNUNET_OK; 1677 return GNUNET_OK;
1538} 1678}
1539 1679
@@ -1548,19 +1688,51 @@ static int
1548client_connect_put (struct Session *s) 1688client_connect_put (struct Session *s)
1549{ 1689{
1550 CURLMcode mret; 1690 CURLMcode mret;
1691 struct HttpAddress *ha;
1692 uint32_t options;
1551 1693
1694 ha = (struct HttpAddress *) s->address->address;
1695 options = ntohl (ha->options);
1552 /* create put request */ 1696 /* create put request */
1553 LOG (GNUNET_ERROR_TYPE_DEBUG, 1697 LOG (GNUNET_ERROR_TYPE_DEBUG,
1554 "Session %p: Init PUT handle\n", s); 1698 "Session %p: Init PUT handle\n",
1699 s);
1555 s->put.easyhandle = curl_easy_init (); 1700 s->put.easyhandle = curl_easy_init ();
1556 s->put.s = s; 1701 s->put.s = s;
1557#if VERBOSE_CURL 1702#if VERBOSE_CURL
1558 curl_easy_setopt (s->put.easyhandle, CURLOPT_VERBOSE, 1L); 1703 curl_easy_setopt (s->put.easyhandle,
1559 curl_easy_setopt (s->put.easyhandle, CURLOPT_DEBUGFUNCTION, &client_log); 1704 CURLOPT_VERBOSE,
1560 curl_easy_setopt (s->put.easyhandle, CURLOPT_DEBUGDATA, &s->put); 1705 1L);
1706 curl_easy_setopt (s->put.easyhandle,
1707 CURLOPT_DEBUGFUNCTION,
1708 &client_log);
1709 curl_easy_setopt (s->put.easyhandle,
1710 CURLOPT_DEBUGDATA,
1711 &s->put);
1561#endif 1712#endif
1713 if (0 != (options & HTTP_OPTIONS_TCP_STEALTH))
1714 {
1715#ifdef SO_TCPSTEALTH
1716 curl_easy_setopt (s->put.easyhandle,
1717 CURLOPT_OPENSOCKETFUNCTION,
1718 &open_tcp_stealth_socket_cb);
1719 curl_easy_setopt (s->put.easyhandle,
1720 CURLOPT_OPENSOCKETDATA,
1721 s);
1722#else
1723 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
1724 "Cannot connect, TCP STEALTH needed and not supported by kernel.\n");
1725 curl_easy_cleanup (s->put.easyhandle);
1726 s->put.easyhandle = NULL;
1727 s->put.s = NULL;
1728 s->put.state = H_DISCONNECTED;
1729 return GNUNET_SYSERR;
1730#endif
1731 }
1562#if BUILD_HTTPS 1732#if BUILD_HTTPS
1563 curl_easy_setopt (s->put.easyhandle, CURLOPT_SSLVERSION, CURL_SSLVERSION_TLSv1); 1733 curl_easy_setopt (s->put.easyhandle,
1734 CURLOPT_SSLVERSION,
1735 CURL_SSLVERSION_TLSv1);
1564 { 1736 {
1565 struct HttpAddress *ha; 1737 struct HttpAddress *ha;
1566 ha = (struct HttpAddress *) s->address->address; 1738 ha = (struct HttpAddress *) s->address->address;
@@ -1568,48 +1740,86 @@ client_connect_put (struct Session *s)
1568 if (HTTP_OPTIONS_VERIFY_CERTIFICATE == 1740 if (HTTP_OPTIONS_VERIFY_CERTIFICATE ==
1569 (ntohl (ha->options) & HTTP_OPTIONS_VERIFY_CERTIFICATE)) 1741 (ntohl (ha->options) & HTTP_OPTIONS_VERIFY_CERTIFICATE))
1570 { 1742 {
1571 curl_easy_setopt (s->put.easyhandle, CURLOPT_SSL_VERIFYPEER, 1L); 1743 curl_easy_setopt (s->put.easyhandle,
1572 curl_easy_setopt (s->put.easyhandle, CURLOPT_SSL_VERIFYHOST, 2L); 1744 CURLOPT_SSL_VERIFYPEER,
1745 1L);
1746 curl_easy_setopt (s->put.easyhandle,
1747 CURLOPT_SSL_VERIFYHOST,
1748 2L);
1573 } 1749 }
1574 else 1750 else
1575 { 1751 {
1576 curl_easy_setopt (s->put.easyhandle, CURLOPT_SSL_VERIFYPEER, 0); 1752 curl_easy_setopt (s->put.easyhandle,
1577 curl_easy_setopt (s->put.easyhandle, CURLOPT_SSL_VERIFYHOST, 0); 1753 CURLOPT_SSL_VERIFYPEER,
1754 0L);
1755 curl_easy_setopt (s->put.easyhandle,
1756 CURLOPT_SSL_VERIFYHOST,
1757 0L);
1578 } 1758 }
1579 } 1759 }
1580 curl_easy_setopt (s->put.easyhandle, CURLOPT_PROTOCOLS, CURLPROTO_HTTPS); 1760 curl_easy_setopt (s->put.easyhandle,
1581 curl_easy_setopt (s->put.easyhandle, CURLOPT_REDIR_PROTOCOLS, CURLPROTO_HTTPS); 1761 CURLOPT_PROTOCOLS,
1762 CURLPROTO_HTTPS);
1763 curl_easy_setopt (s->put.easyhandle,
1764 CURLOPT_REDIR_PROTOCOLS,
1765 CURLPROTO_HTTPS);
1582#else 1766#else
1583 curl_easy_setopt (s->put.easyhandle, CURLOPT_PROTOCOLS, CURLPROTO_HTTP); 1767 curl_easy_setopt (s->put.easyhandle,
1584 curl_easy_setopt (s->put.easyhandle, CURLOPT_REDIR_PROTOCOLS, CURLPROTO_HTTP); 1768 CURLOPT_PROTOCOLS,
1769 CURLPROTO_HTTP);
1770 curl_easy_setopt (s->put.easyhandle,
1771 CURLOPT_REDIR_PROTOCOLS,
1772 CURLPROTO_HTTP);
1585#endif 1773#endif
1586 if (s->plugin->proxy_hostname != NULL) 1774 if (NULL != s->plugin->proxy_hostname)
1587 { 1775 {
1588 curl_easy_setopt (s->put.easyhandle, CURLOPT_PROXY, s->plugin->proxy_hostname); 1776 curl_easy_setopt (s->put.easyhandle,
1589 curl_easy_setopt (s->put.easyhandle, CURLOPT_PROXYTYPE, s->plugin->proxytype); 1777 CURLOPT_PROXY,
1778 s->plugin->proxy_hostname);
1779 curl_easy_setopt (s->put.easyhandle,
1780 CURLOPT_PROXYTYPE,
1781 s->plugin->proxytype);
1590 if (NULL != s->plugin->proxy_username) 1782 if (NULL != s->plugin->proxy_username)
1591 curl_easy_setopt (s->put.easyhandle, CURLOPT_PROXYUSERNAME, 1783 curl_easy_setopt (s->put.easyhandle,
1592 s->plugin->proxy_username); 1784 CURLOPT_PROXYUSERNAME,
1785 s->plugin->proxy_username);
1593 if (NULL != s->plugin->proxy_password) 1786 if (NULL != s->plugin->proxy_password)
1594 curl_easy_setopt (s->put.easyhandle, CURLOPT_PROXYPASSWORD, 1787 curl_easy_setopt (s->put.easyhandle,
1595 s->plugin->proxy_password); 1788 CURLOPT_PROXYPASSWORD,
1789 s->plugin->proxy_password);
1596 if (GNUNET_YES == s->plugin->proxy_use_httpproxytunnel) 1790 if (GNUNET_YES == s->plugin->proxy_use_httpproxytunnel)
1597 curl_easy_setopt (s->put.easyhandle, CURLOPT_HTTPPROXYTUNNEL, 1791 curl_easy_setopt (s->put.easyhandle,
1598 s->plugin->proxy_use_httpproxytunnel); 1792 CURLOPT_HTTPPROXYTUNNEL,
1793 s->plugin->proxy_use_httpproxytunnel);
1599 } 1794 }
1600 1795
1601 curl_easy_setopt (s->put.easyhandle, CURLOPT_URL, s->url); 1796 curl_easy_setopt (s->put.easyhandle,
1602 curl_easy_setopt (s->put.easyhandle, CURLOPT_UPLOAD, 1L); 1797 CURLOPT_URL,
1603 //curl_easy_setopt (s->put.easyhandle, CURLOPT_HEADERFUNCTION, &client_curl_header); 1798 s->url);
1604 //curl_easy_setopt (s->put.easyhandle, CURLOPT_WRITEHEADER, ps); 1799 curl_easy_setopt (s->put.easyhandle,
1605 curl_easy_setopt (s->put.easyhandle, CURLOPT_READFUNCTION, client_send_cb); 1800 CURLOPT_UPLOAD,
1606 curl_easy_setopt (s->put.easyhandle, CURLOPT_READDATA, s); 1801 1L);
1607 curl_easy_setopt (s->put.easyhandle, CURLOPT_WRITEFUNCTION, client_receive_put); 1802 curl_easy_setopt (s->put.easyhandle,
1608 curl_easy_setopt (s->put.easyhandle, CURLOPT_WRITEDATA, s); 1803 CURLOPT_READFUNCTION,
1804 &client_send_cb);
1805 curl_easy_setopt (s->put.easyhandle,
1806 CURLOPT_READDATA,
1807 s);
1808 curl_easy_setopt (s->put.easyhandle,
1809 CURLOPT_WRITEFUNCTION,
1810 &client_receive_put);
1811 curl_easy_setopt (s->put.easyhandle,
1812 CURLOPT_WRITEDATA,
1813 s);
1609 /* No timeout by default, timeout done with session timeout */ 1814 /* No timeout by default, timeout done with session timeout */
1610 curl_easy_setopt (s->put.easyhandle, CURLOPT_TIMEOUT, 0); 1815 curl_easy_setopt (s->put.easyhandle,
1611 curl_easy_setopt (s->put.easyhandle, CURLOPT_PRIVATE, s); 1816 CURLOPT_TIMEOUT,
1612 curl_easy_setopt (s->put.easyhandle, CURLOPT_CONNECTTIMEOUT_MS, 1817 0L);
1818 curl_easy_setopt (s->put.easyhandle,
1819 CURLOPT_PRIVATE,
1820 s);
1821 curl_easy_setopt (s->put.easyhandle,
1822 CURLOPT_CONNECTTIMEOUT_MS,
1613 (long) (HTTP_CLIENT_NOT_VALIDATED_TIMEOUT.rel_value_us / 1000LL)); 1823 (long) (HTTP_CLIENT_NOT_VALIDATED_TIMEOUT.rel_value_us / 1000LL));
1614 curl_easy_setopt (s->put.easyhandle, CURLOPT_BUFFERSIZE, 1824 curl_easy_setopt (s->put.easyhandle, CURLOPT_BUFFERSIZE,
1615 2 * GNUNET_SERVER_MAX_MESSAGE_SIZE); 1825 2 * GNUNET_SERVER_MAX_MESSAGE_SIZE);
@@ -1625,7 +1835,6 @@ client_connect_put (struct Session *s)
1625 s, curl_multi_strerror (mret)); 1835 s, curl_multi_strerror (mret));
1626 curl_easy_cleanup (s->put.easyhandle); 1836 curl_easy_cleanup (s->put.easyhandle);
1627 s->put.easyhandle = NULL; 1837 s->put.easyhandle = NULL;
1628 s->put.easyhandle = NULL;
1629 s->put.s = NULL; 1838 s->put.s = NULL;
1630 s->put.state = H_DISCONNECTED; 1839 s->put.state = H_DISCONNECTED;
1631 return GNUNET_SYSERR; 1840 return GNUNET_SYSERR;
@@ -1654,18 +1863,24 @@ client_connect (struct Session *s)
1654 int res = GNUNET_OK; 1863 int res = GNUNET_OK;
1655 1864
1656 /* create url */ 1865 /* create url */
1657 if (NULL == http_common_plugin_address_to_string(plugin->protocol, 1866 if (NULL ==
1658 s->address->address, s->address->address_length)) 1867 http_common_plugin_address_to_string(plugin->protocol,
1659 { 1868 s->address->address,
1660 LOG(GNUNET_ERROR_TYPE_DEBUG, "Invalid address peer `%s'\n", 1869 s->address->address_length))
1661 GNUNET_i2s(&s->address->peer)); 1870 {
1662 return GNUNET_SYSERR; 1871 LOG (GNUNET_ERROR_TYPE_DEBUG,
1663 } 1872 "Invalid address peer `%s'\n",
1873 GNUNET_i2s(&s->address->peer));
1874 return GNUNET_SYSERR;
1875 }
1664 1876
1665 GNUNET_asprintf(&s->url, "%s/%s;%u", 1877 GNUNET_asprintf(&s->url,
1666 http_common_plugin_address_to_url(NULL, s->address->address, 1878 "%s/%s;%u",
1667 s->address->address_length), 1879 http_common_plugin_address_to_url(NULL,
1668 GNUNET_i2s_full(plugin->env->my_identity), plugin->last_tag); 1880 s->address->address,
1881 s->address->address_length),
1882 GNUNET_i2s_full (plugin->env->my_identity),
1883 plugin->last_tag);
1669 1884
1670 plugin->last_tag++; 1885 plugin->last_tag++;
1671 LOG (GNUNET_ERROR_TYPE_DEBUG, 1886 LOG (GNUNET_ERROR_TYPE_DEBUG,
@@ -1798,7 +2013,9 @@ http_client_plugin_get_session (void *cls,
1798 /* Determine network location */ 2013 /* Determine network location */
1799 ats.type = htonl (GNUNET_ATS_NETWORK_TYPE); 2014 ats.type = htonl (GNUNET_ATS_NETWORK_TYPE);
1800 ats.value = htonl (GNUNET_ATS_NET_UNSPECIFIED); 2015 ats.value = htonl (GNUNET_ATS_NET_UNSPECIFIED);
1801 sa = http_common_socket_from_address (address->address, address->address_length, &res); 2016 sa = http_common_socket_from_address (address->address,
2017 address->address_length,
2018 &res);
1802 if (GNUNET_SYSERR == res) 2019 if (GNUNET_SYSERR == res)
1803 return NULL; 2020 return NULL;
1804 if (GNUNET_YES == res) 2021 if (GNUNET_YES == res)
@@ -1975,7 +2192,6 @@ client_configure_plugin (struct HTTP_Client_Plugin *plugin)
1975 unsigned long long max_requests; 2192 unsigned long long max_requests;
1976 char *proxy_type; 2193 char *proxy_type;
1977 2194
1978
1979 /* Optional parameters */ 2195 /* Optional parameters */
1980 if (GNUNET_OK != 2196 if (GNUNET_OK !=
1981 GNUNET_CONFIGURATION_get_value_number (plugin->env->cfg, 2197 GNUNET_CONFIGURATION_get_value_number (plugin->env->cfg,
@@ -1990,8 +2206,11 @@ client_configure_plugin (struct HTTP_Client_Plugin *plugin)
1990 plugin->max_requests); 2206 plugin->max_requests);
1991 2207
1992 /* Read proxy configuration */ 2208 /* Read proxy configuration */
1993 if (GNUNET_OK == GNUNET_CONFIGURATION_get_value_string (plugin->env->cfg, 2209 if (GNUNET_OK ==
1994 plugin->name, "PROXY", &plugin->proxy_hostname)) 2210 GNUNET_CONFIGURATION_get_value_string (plugin->env->cfg,
2211 plugin->name,
2212 "PROXY",
2213 &plugin->proxy_hostname))
1995 { 2214 {
1996 LOG (GNUNET_ERROR_TYPE_DEBUG, 2215 LOG (GNUNET_ERROR_TYPE_DEBUG,
1997 "Found proxy host: `%s'\n", 2216 "Found proxy host: `%s'\n",
diff --git a/src/transport/plugin_transport_http_common.h b/src/transport/plugin_transport_http_common.h
index 79c671862..ccb597b92 100644
--- a/src/transport/plugin_transport_http_common.h
+++ b/src/transport/plugin_transport_http_common.h
@@ -1,6 +1,6 @@
1/* 1/*
2 This file is part of GNUnet 2 This file is part of GNUnet
3 (C) 2002-2013 Christian Grothoff (and other contributing authors) 3 (C) 2002-2014 Christian Grothoff (and other contributing authors)
4 4
5 GNUnet is free software; you can redistribute it and/or modify 5 GNUnet is free software; you can redistribute it and/or modify
6 it under the terms of the GNU General Public License as published 6 it under the terms of the GNU General Public License as published
@@ -21,6 +21,7 @@
21 * @file transport/plugin_transport_http_common.c 21 * @file transport/plugin_transport_http_common.c
22 * @brief functionality shared by http client and server transport service plugin 22 * @brief functionality shared by http client and server transport service plugin
23 * @author Matthias Wachs 23 * @author Matthias Wachs
24 * @author Christian Grothoff
24 */ 25 */
25#include "platform.h" 26#include "platform.h"
26#include "gnunet_common.h" 27#include "gnunet_common.h"
@@ -72,7 +73,12 @@ enum HttpAddressOptions
72 * (if this bit is not set, it is probably just self- 73 * (if this bit is not set, it is probably just self-
73 * signed and not expected to be verified). 74 * signed and not expected to be verified).
74 */ 75 */
75 HTTP_OPTIONS_VERIFY_CERTIFICATE = 1 76 HTTP_OPTIONS_VERIFY_CERTIFICATE = 1,
77
78 /**
79 * Enable TCP Stealth-style port knocking.
80 */
81 HTTP_OPTIONS_TCP_STEALTH = 2
76}; 82};
77 83
78 84