diff options
Diffstat (limited to 'src/gns/gnunet-gns-proxy.c')
-rw-r--r-- | src/gns/gnunet-gns-proxy.c | 4189 |
1 files changed, 2112 insertions, 2077 deletions
diff --git a/src/gns/gnunet-gns-proxy.c b/src/gns/gnunet-gns-proxy.c index 6285a8fcd..2a39efef2 100644 --- a/src/gns/gnunet-gns-proxy.c +++ b/src/gns/gnunet-gns-proxy.c | |||
@@ -94,13 +94,15 @@ | |||
94 | /** | 94 | /** |
95 | * After how long do we clean up unused MHD TLS instances? | 95 | * After how long do we clean up unused MHD TLS instances? |
96 | */ | 96 | */ |
97 | #define MHD_CACHE_TIMEOUT GNUNET_TIME_relative_multiply(GNUNET_TIME_UNIT_MINUTES, 5) | 97 | #define MHD_CACHE_TIMEOUT GNUNET_TIME_relative_multiply ( \ |
98 | GNUNET_TIME_UNIT_MINUTES, 5) | ||
98 | 99 | ||
99 | /** | 100 | /** |
100 | * After how long do we clean up Socks5 handles that failed to show any activity | 101 | * After how long do we clean up Socks5 handles that failed to show any activity |
101 | * with their respective MHD instance? | 102 | * with their respective MHD instance? |
102 | */ | 103 | */ |
103 | #define HTTP_HANDSHAKE_TIMEOUT GNUNET_TIME_relative_multiply(GNUNET_TIME_UNIT_SECONDS, 15) | 104 | #define HTTP_HANDSHAKE_TIMEOUT GNUNET_TIME_relative_multiply ( \ |
105 | GNUNET_TIME_UNIT_SECONDS, 15) | ||
104 | 106 | ||
105 | 107 | ||
106 | /** | 108 | /** |
@@ -111,12 +113,12 @@ | |||
111 | * @param rc return code from curl | 113 | * @param rc return code from curl |
112 | */ | 114 | */ |
113 | #define LOG_CURL_EASY(level, fun, rc) \ | 115 | #define LOG_CURL_EASY(level, fun, rc) \ |
114 | GNUNET_log(level, \ | 116 | GNUNET_log (level, \ |
115 | _("%s failed at %s:%d: `%s'\n"), \ | 117 | _ ("%s failed at %s:%d: `%s'\n"), \ |
116 | fun, \ | 118 | fun, \ |
117 | __FILE__, \ | 119 | __FILE__, \ |
118 | __LINE__, \ | 120 | __LINE__, \ |
119 | curl_easy_strerror(rc)) | 121 | curl_easy_strerror (rc)) |
120 | 122 | ||
121 | 123 | ||
122 | /* *************** Socks protocol definitions (move to TUN?) ****************** */ | 124 | /* *************** Socks protocol definitions (move to TUN?) ****************** */ |
@@ -135,7 +137,8 @@ | |||
135 | /** | 137 | /** |
136 | * Commands in Socks5. | 138 | * Commands in Socks5. |
137 | */ | 139 | */ |
138 | enum Socks5Commands { | 140 | enum Socks5Commands |
141 | { | ||
139 | /** | 142 | /** |
140 | * Establish TCP/IP stream. | 143 | * Establish TCP/IP stream. |
141 | */ | 144 | */ |
@@ -156,7 +159,8 @@ enum Socks5Commands { | |||
156 | /** | 159 | /** |
157 | * Address types in Socks5. | 160 | * Address types in Socks5. |
158 | */ | 161 | */ |
159 | enum Socks5AddressType { | 162 | enum Socks5AddressType |
163 | { | ||
160 | /** | 164 | /** |
161 | * IPv4 address. | 165 | * IPv4 address. |
162 | */ | 166 | */ |
@@ -177,7 +181,8 @@ enum Socks5AddressType { | |||
177 | /** | 181 | /** |
178 | * Status codes in Socks5 response. | 182 | * Status codes in Socks5 response. |
179 | */ | 183 | */ |
180 | enum Socks5StatusCode { | 184 | enum Socks5StatusCode |
185 | { | ||
181 | SOCKS5_STATUS_REQUEST_GRANTED = 0, | 186 | SOCKS5_STATUS_REQUEST_GRANTED = 0, |
182 | SOCKS5_STATUS_GENERAL_FAILURE = 1, | 187 | SOCKS5_STATUS_GENERAL_FAILURE = 1, |
183 | SOCKS5_STATUS_CONNECTION_NOT_ALLOWED_BY_RULE = 2, | 188 | SOCKS5_STATUS_CONNECTION_NOT_ALLOWED_BY_RULE = 2, |
@@ -193,7 +198,8 @@ enum Socks5StatusCode { | |||
193 | /** | 198 | /** |
194 | * Client hello in Socks5 protocol. | 199 | * Client hello in Socks5 protocol. |
195 | */ | 200 | */ |
196 | struct Socks5ClientHelloMessage { | 201 | struct Socks5ClientHelloMessage |
202 | { | ||
197 | /** | 203 | /** |
198 | * Should be #SOCKS_VERSION_5. | 204 | * Should be #SOCKS_VERSION_5. |
199 | */ | 205 | */ |
@@ -211,7 +217,8 @@ struct Socks5ClientHelloMessage { | |||
211 | /** | 217 | /** |
212 | * Server hello in Socks5 protocol. | 218 | * Server hello in Socks5 protocol. |
213 | */ | 219 | */ |
214 | struct Socks5ServerHelloMessage { | 220 | struct Socks5ServerHelloMessage |
221 | { | ||
215 | /** | 222 | /** |
216 | * Should be #SOCKS_VERSION_5. | 223 | * Should be #SOCKS_VERSION_5. |
217 | */ | 224 | */ |
@@ -228,7 +235,8 @@ struct Socks5ServerHelloMessage { | |||
228 | /** | 235 | /** |
229 | * Client socks request in Socks5 protocol. | 236 | * Client socks request in Socks5 protocol. |
230 | */ | 237 | */ |
231 | struct Socks5ClientRequestMessage { | 238 | struct Socks5ClientRequestMessage |
239 | { | ||
232 | /** | 240 | /** |
233 | * Should be #SOCKS_VERSION_5. | 241 | * Should be #SOCKS_VERSION_5. |
234 | */ | 242 | */ |
@@ -260,7 +268,8 @@ struct Socks5ClientRequestMessage { | |||
260 | /** | 268 | /** |
261 | * Server response to client requests in Socks5 protocol. | 269 | * Server response to client requests in Socks5 protocol. |
262 | */ | 270 | */ |
263 | struct Socks5ServerResponseMessage { | 271 | struct Socks5ServerResponseMessage |
272 | { | ||
264 | /** | 273 | /** |
265 | * Should be #SOCKS_VERSION_5. | 274 | * Should be #SOCKS_VERSION_5. |
266 | */ | 275 | */ |
@@ -295,7 +304,8 @@ struct Socks5ServerResponseMessage { | |||
295 | /** | 304 | /** |
296 | * A structure for CA cert/key | 305 | * A structure for CA cert/key |
297 | */ | 306 | */ |
298 | struct ProxyCA { | 307 | struct ProxyCA |
308 | { | ||
299 | /** | 309 | /** |
300 | * The certificate | 310 | * The certificate |
301 | */ | 311 | */ |
@@ -311,7 +321,8 @@ struct ProxyCA { | |||
311 | /** | 321 | /** |
312 | * Structure for GNS certificates | 322 | * Structure for GNS certificates |
313 | */ | 323 | */ |
314 | struct ProxyGNSCertificate { | 324 | struct ProxyGNSCertificate |
325 | { | ||
315 | /** | 326 | /** |
316 | * The certificate as PEM | 327 | * The certificate as PEM |
317 | */ | 328 | */ |
@@ -328,7 +339,8 @@ struct ProxyGNSCertificate { | |||
328 | /** | 339 | /** |
329 | * A structure for all running Httpds | 340 | * A structure for all running Httpds |
330 | */ | 341 | */ |
331 | struct MhdHttpList { | 342 | struct MhdHttpList |
343 | { | ||
332 | /** | 344 | /** |
333 | * DLL for httpds | 345 | * DLL for httpds |
334 | */ | 346 | */ |
@@ -372,7 +384,8 @@ struct MhdHttpList { | |||
372 | /** | 384 | /** |
373 | * The socks phases. | 385 | * The socks phases. |
374 | */ | 386 | */ |
375 | enum SocksPhase { | 387 | enum SocksPhase |
388 | { | ||
376 | /** | 389 | /** |
377 | * We're waiting to get the client hello. | 390 | * We're waiting to get the client hello. |
378 | */ | 391 | */ |
@@ -428,7 +441,8 @@ enum SocksPhase { | |||
428 | /** | 441 | /** |
429 | * A header list | 442 | * A header list |
430 | */ | 443 | */ |
431 | struct HttpResponseHeader { | 444 | struct HttpResponseHeader |
445 | { | ||
432 | /** | 446 | /** |
433 | * DLL | 447 | * DLL |
434 | */ | 448 | */ |
@@ -453,7 +467,8 @@ struct HttpResponseHeader { | |||
453 | /** | 467 | /** |
454 | * A structure for socks requests | 468 | * A structure for socks requests |
455 | */ | 469 | */ |
456 | struct Socks5Request { | 470 | struct Socks5Request |
471 | { | ||
457 | /** | 472 | /** |
458 | * DLL. | 473 | * DLL. |
459 | */ | 474 | */ |
@@ -673,17 +688,17 @@ static struct GNUNET_NETWORK_Handle *lsock6; | |||
673 | /** | 688 | /** |
674 | * The listen task ID for IPv4 | 689 | * The listen task ID for IPv4 |
675 | */ | 690 | */ |
676 | static struct GNUNET_SCHEDULER_Task * ltask4; | 691 | static struct GNUNET_SCHEDULER_Task *ltask4; |
677 | 692 | ||
678 | /** | 693 | /** |
679 | * The listen task ID for IPv6 | 694 | * The listen task ID for IPv6 |
680 | */ | 695 | */ |
681 | static struct GNUNET_SCHEDULER_Task * ltask6; | 696 | static struct GNUNET_SCHEDULER_Task *ltask6; |
682 | 697 | ||
683 | /** | 698 | /** |
684 | * The cURL download task (curl multi API). | 699 | * The cURL download task (curl multi API). |
685 | */ | 700 | */ |
686 | static struct GNUNET_SCHEDULER_Task * curl_download_task; | 701 | static struct GNUNET_SCHEDULER_Task *curl_download_task; |
687 | 702 | ||
688 | /** | 703 | /** |
689 | * The cURL multi handle | 704 | * The cURL multi handle |
@@ -751,7 +766,7 @@ static const struct GNUNET_CONFIGURATION_Handle *cfg; | |||
751 | * @param hd the daemon to run now. | 766 | * @param hd the daemon to run now. |
752 | */ | 767 | */ |
753 | static void | 768 | static void |
754 | run_mhd_now(struct MhdHttpList *hd); | 769 | run_mhd_now (struct MhdHttpList *hd); |
755 | 770 | ||
756 | 771 | ||
757 | /** | 772 | /** |
@@ -760,79 +775,79 @@ run_mhd_now(struct MhdHttpList *hd); | |||
760 | * @param s5r the handle to destroy | 775 | * @param s5r the handle to destroy |
761 | */ | 776 | */ |
762 | static void | 777 | static void |
763 | cleanup_s5r(struct Socks5Request *s5r) | 778 | cleanup_s5r (struct Socks5Request *s5r) |
764 | { | 779 | { |
765 | GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, | 780 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
766 | "Cleaning up socks request\n"); | 781 | "Cleaning up socks request\n"); |
767 | if (NULL != s5r->curl) | 782 | if (NULL != s5r->curl) |
768 | { | 783 | { |
769 | GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, | 784 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
770 | "Cleaning up cURL handle\n"); | 785 | "Cleaning up cURL handle\n"); |
771 | curl_multi_remove_handle(curl_multi, | 786 | curl_multi_remove_handle (curl_multi, |
772 | s5r->curl); | 787 | s5r->curl); |
773 | curl_easy_cleanup(s5r->curl); | 788 | curl_easy_cleanup (s5r->curl); |
774 | s5r->curl = NULL; | 789 | s5r->curl = NULL; |
775 | } | 790 | } |
776 | if (s5r->suspended) | 791 | if (s5r->suspended) |
777 | { | 792 | { |
778 | s5r->suspended = GNUNET_NO; | 793 | s5r->suspended = GNUNET_NO; |
779 | MHD_resume_connection(s5r->con); | 794 | MHD_resume_connection (s5r->con); |
780 | } | 795 | } |
781 | curl_slist_free_all(s5r->headers); | 796 | curl_slist_free_all (s5r->headers); |
782 | if (NULL != s5r->hosts) | 797 | if (NULL != s5r->hosts) |
783 | { | 798 | { |
784 | curl_slist_free_all(s5r->hosts); | 799 | curl_slist_free_all (s5r->hosts); |
785 | } | 800 | } |
786 | if ((NULL != s5r->response) && | 801 | if ((NULL != s5r->response) && |
787 | (curl_failure_response != s5r->response)) | 802 | (curl_failure_response != s5r->response)) |
788 | { | 803 | { |
789 | MHD_destroy_response(s5r->response); | 804 | MHD_destroy_response (s5r->response); |
790 | s5r->response = NULL; | 805 | s5r->response = NULL; |
791 | } | 806 | } |
792 | if (NULL != s5r->rtask) | 807 | if (NULL != s5r->rtask) |
793 | { | 808 | { |
794 | GNUNET_SCHEDULER_cancel(s5r->rtask); | 809 | GNUNET_SCHEDULER_cancel (s5r->rtask); |
795 | s5r->rtask = NULL; | 810 | s5r->rtask = NULL; |
796 | } | 811 | } |
797 | if (NULL != s5r->timeout_task) | 812 | if (NULL != s5r->timeout_task) |
798 | { | 813 | { |
799 | GNUNET_SCHEDULER_cancel(s5r->timeout_task); | 814 | GNUNET_SCHEDULER_cancel (s5r->timeout_task); |
800 | s5r->timeout_task = NULL; | 815 | s5r->timeout_task = NULL; |
801 | } | 816 | } |
802 | if (NULL != s5r->wtask) | 817 | if (NULL != s5r->wtask) |
803 | { | 818 | { |
804 | GNUNET_SCHEDULER_cancel(s5r->wtask); | 819 | GNUNET_SCHEDULER_cancel (s5r->wtask); |
805 | s5r->wtask = NULL; | 820 | s5r->wtask = NULL; |
806 | } | 821 | } |
807 | if (NULL != s5r->gns_lookup) | 822 | if (NULL != s5r->gns_lookup) |
808 | { | 823 | { |
809 | GNUNET_GNS_lookup_with_tld_cancel(s5r->gns_lookup); | 824 | GNUNET_GNS_lookup_with_tld_cancel (s5r->gns_lookup); |
810 | s5r->gns_lookup = NULL; | 825 | s5r->gns_lookup = NULL; |
811 | } | 826 | } |
812 | if (NULL != s5r->sock) | 827 | if (NULL != s5r->sock) |
813 | { | 828 | { |
814 | if (SOCKS5_SOCKET_WITH_MHD <= s5r->state) | 829 | if (SOCKS5_SOCKET_WITH_MHD <= s5r->state) |
815 | GNUNET_NETWORK_socket_free_memory_only_(s5r->sock); | 830 | GNUNET_NETWORK_socket_free_memory_only_ (s5r->sock); |
816 | else | 831 | else |
817 | GNUNET_NETWORK_socket_close(s5r->sock); | 832 | GNUNET_NETWORK_socket_close (s5r->sock); |
818 | s5r->sock = NULL; | 833 | s5r->sock = NULL; |
819 | } | 834 | } |
820 | GNUNET_CONTAINER_DLL_remove(s5r_head, | 835 | GNUNET_CONTAINER_DLL_remove (s5r_head, |
821 | s5r_tail, | 836 | s5r_tail, |
822 | s5r); | 837 | s5r); |
823 | GNUNET_free_non_null(s5r->domain); | 838 | GNUNET_free_non_null (s5r->domain); |
824 | GNUNET_free_non_null(s5r->leho); | 839 | GNUNET_free_non_null (s5r->leho); |
825 | GNUNET_free_non_null(s5r->url); | 840 | GNUNET_free_non_null (s5r->url); |
826 | for (unsigned int i = 0; i < s5r->num_danes; i++) | 841 | for (unsigned int i = 0; i < s5r->num_danes; i++) |
827 | GNUNET_free(s5r->dane_data[i]); | 842 | GNUNET_free (s5r->dane_data[i]); |
828 | GNUNET_free(s5r); | 843 | GNUNET_free (s5r); |
829 | } | 844 | } |
830 | 845 | ||
831 | 846 | ||
832 | /* ************************* HTTP handling with cURL *********************** */ | 847 | /* ************************* HTTP handling with cURL *********************** */ |
833 | 848 | ||
834 | static void | 849 | static void |
835 | curl_download_prepare(); | 850 | curl_download_prepare (); |
836 | 851 | ||
837 | 852 | ||
838 | /** | 853 | /** |
@@ -847,89 +862,89 @@ curl_download_prepare(); | |||
847 | * @return number of bytes written to @a buf | 862 | * @return number of bytes written to @a buf |
848 | */ | 863 | */ |
849 | static ssize_t | 864 | static ssize_t |
850 | mhd_content_cb(void *cls, | 865 | mhd_content_cb (void *cls, |
851 | uint64_t pos, | 866 | uint64_t pos, |
852 | char* buf, | 867 | char*buf, |
853 | size_t max) | 868 | size_t max) |
854 | { | 869 | { |
855 | struct Socks5Request *s5r = cls; | 870 | struct Socks5Request *s5r = cls; |
856 | size_t bytes_to_copy; | 871 | size_t bytes_to_copy; |
857 | 872 | ||
858 | if ((SOCKS5_SOCKET_UPLOAD_STARTED == s5r->state) || | 873 | if ((SOCKS5_SOCKET_UPLOAD_STARTED == s5r->state) || |
859 | (SOCKS5_SOCKET_UPLOAD_DONE == s5r->state)) | 874 | (SOCKS5_SOCKET_UPLOAD_DONE == s5r->state)) |
860 | { | 875 | { |
861 | /* we're still not done with the upload, do not yet | 876 | /* we're still not done with the upload, do not yet |
862 | start the download, the IO buffer is still full | 877 | start the download, the IO buffer is still full |
863 | with upload data. */ | 878 | with upload data. */ |
864 | GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, | 879 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
865 | "Pausing MHD download %s%s, not yet ready for download\n", | 880 | "Pausing MHD download %s%s, not yet ready for download\n", |
866 | s5r->domain, | 881 | s5r->domain, |
867 | s5r->url); | 882 | s5r->url); |
868 | return 0; /* not yet ready for data download */ | 883 | return 0; /* not yet ready for data download */ |
869 | } | 884 | } |
870 | bytes_to_copy = GNUNET_MIN(max, | 885 | bytes_to_copy = GNUNET_MIN (max, |
871 | s5r->io_len); | 886 | s5r->io_len); |
872 | if ((0 == bytes_to_copy) && | 887 | if ((0 == bytes_to_copy) && |
873 | (SOCKS5_SOCKET_DOWNLOAD_DONE != s5r->state)) | 888 | (SOCKS5_SOCKET_DOWNLOAD_DONE != s5r->state)) |
889 | { | ||
890 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
891 | "Pausing MHD download %s%s, no data available\n", | ||
892 | s5r->domain, | ||
893 | s5r->url); | ||
894 | if (NULL != s5r->curl) | ||
895 | { | ||
896 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
897 | "Continuing CURL interaction for %s%s\n", | ||
898 | s5r->domain, | ||
899 | s5r->url); | ||
900 | if (GNUNET_YES == s5r->curl_paused) | ||
901 | { | ||
902 | s5r->curl_paused = GNUNET_NO; | ||
903 | curl_easy_pause (s5r->curl, | ||
904 | CURLPAUSE_CONT); | ||
905 | } | ||
906 | curl_download_prepare (); | ||
907 | } | ||
908 | if (GNUNET_NO == s5r->suspended) | ||
874 | { | 909 | { |
875 | GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, | 910 | MHD_suspend_connection (s5r->con); |
876 | "Pausing MHD download %s%s, no data available\n", | 911 | s5r->suspended = GNUNET_YES; |
877 | s5r->domain, | ||
878 | s5r->url); | ||
879 | if (NULL != s5r->curl) | ||
880 | { | ||
881 | GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, | ||
882 | "Continuing CURL interaction for %s%s\n", | ||
883 | s5r->domain, | ||
884 | s5r->url); | ||
885 | if (GNUNET_YES == s5r->curl_paused) | ||
886 | { | ||
887 | s5r->curl_paused = GNUNET_NO; | ||
888 | curl_easy_pause(s5r->curl, | ||
889 | CURLPAUSE_CONT); | ||
890 | } | ||
891 | curl_download_prepare(); | ||
892 | } | ||
893 | if (GNUNET_NO == s5r->suspended) | ||
894 | { | ||
895 | MHD_suspend_connection(s5r->con); | ||
896 | s5r->suspended = GNUNET_YES; | ||
897 | } | ||
898 | return 0; /* more data later */ | ||
899 | } | 912 | } |
913 | return 0; /* more data later */ | ||
914 | } | ||
900 | if ((0 == bytes_to_copy) && | 915 | if ((0 == bytes_to_copy) && |
901 | (SOCKS5_SOCKET_DOWNLOAD_DONE == s5r->state)) | 916 | (SOCKS5_SOCKET_DOWNLOAD_DONE == s5r->state)) |
902 | { | 917 | { |
903 | GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, | 918 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
904 | "Completed MHD download %s%s\n", | 919 | "Completed MHD download %s%s\n", |
905 | s5r->domain, | 920 | s5r->domain, |
906 | s5r->url); | 921 | s5r->url); |
907 | return MHD_CONTENT_READER_END_OF_STREAM; | 922 | return MHD_CONTENT_READER_END_OF_STREAM; |
908 | } | 923 | } |
909 | GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, | 924 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
910 | "Writing %llu/%llu bytes to %s%s\n", | 925 | "Writing %llu/%llu bytes to %s%s\n", |
911 | (unsigned long long)bytes_to_copy, | 926 | (unsigned long long) bytes_to_copy, |
912 | (unsigned long long)s5r->io_len, | 927 | (unsigned long long) s5r->io_len, |
913 | s5r->domain, | 928 | s5r->domain, |
914 | s5r->url); | 929 | s5r->url); |
915 | GNUNET_memcpy(buf, | 930 | GNUNET_memcpy (buf, |
916 | s5r->io_buf, | 931 | s5r->io_buf, |
917 | bytes_to_copy); | 932 | bytes_to_copy); |
918 | memmove(s5r->io_buf, | 933 | memmove (s5r->io_buf, |
919 | &s5r->io_buf[bytes_to_copy], | 934 | &s5r->io_buf[bytes_to_copy], |
920 | s5r->io_len - bytes_to_copy); | 935 | s5r->io_len - bytes_to_copy); |
921 | s5r->io_len -= bytes_to_copy; | 936 | s5r->io_len -= bytes_to_copy; |
922 | if ((NULL != s5r->curl) && | 937 | if ((NULL != s5r->curl) && |
923 | (GNUNET_YES == s5r->curl_paused)) | 938 | (GNUNET_YES == s5r->curl_paused)) |
924 | { | 939 | { |
925 | GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, | 940 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
926 | "Continuing CURL interaction for %s%s\n", | 941 | "Continuing CURL interaction for %s%s\n", |
927 | s5r->domain, | 942 | s5r->domain, |
928 | s5r->url); | 943 | s5r->url); |
929 | s5r->curl_paused = GNUNET_NO; | 944 | s5r->curl_paused = GNUNET_NO; |
930 | curl_easy_pause(s5r->curl, | 945 | curl_easy_pause (s5r->curl, |
931 | CURLPAUSE_CONT); | 946 | CURLPAUSE_CONT); |
932 | } | 947 | } |
933 | return bytes_to_copy; | 948 | return bytes_to_copy; |
934 | } | 949 | } |
935 | 950 | ||
@@ -943,7 +958,7 @@ mhd_content_cb(void *cls, | |||
943 | * @return #GNUNET_OK if the certificate is valid | 958 | * @return #GNUNET_OK if the certificate is valid |
944 | */ | 959 | */ |
945 | static int | 960 | static int |
946 | check_ssl_certificate(struct Socks5Request *s5r) | 961 | check_ssl_certificate (struct Socks5Request *s5r) |
947 | { | 962 | { |
948 | unsigned int cert_list_size; | 963 | unsigned int cert_list_size; |
949 | const gnutls_datum_t *chainp; | 964 | const gnutls_datum_t *chainp; |
@@ -955,113 +970,115 @@ check_ssl_certificate(struct Socks5Request *s5r) | |||
955 | const char *name; | 970 | const char *name; |
956 | 971 | ||
957 | s5r->ssl_checked = GNUNET_YES; | 972 | s5r->ssl_checked = GNUNET_YES; |
958 | GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, | 973 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
959 | "Checking X.509 certificate\n"); | 974 | "Checking X.509 certificate\n"); |
960 | if (CURLE_OK != | 975 | if (CURLE_OK != |
961 | curl_easy_getinfo(s5r->curl, | 976 | curl_easy_getinfo (s5r->curl, |
962 | CURLINFO_TLS_SESSION, | 977 | CURLINFO_TLS_SESSION, |
963 | &tlsinfo)) | 978 | &tlsinfo)) |
964 | return GNUNET_SYSERR; | 979 | return GNUNET_SYSERR; |
965 | if (CURLSSLBACKEND_GNUTLS != tlsinfo->backend) | 980 | if (CURLSSLBACKEND_GNUTLS != tlsinfo->backend) |
966 | { | 981 | { |
967 | GNUNET_log(GNUNET_ERROR_TYPE_ERROR, | 982 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, |
968 | _("Unsupported CURL TLS backend %d\n"), | 983 | _ ("Unsupported CURL TLS backend %d\n"), |
969 | tlsinfo->backend); | 984 | tlsinfo->backend); |
970 | return GNUNET_SYSERR; | 985 | return GNUNET_SYSERR; |
971 | } | 986 | } |
972 | chainp = gnutls_certificate_get_peers(tlsinfo->internals, | 987 | chainp = gnutls_certificate_get_peers (tlsinfo->internals, |
973 | &cert_list_size); | 988 | &cert_list_size); |
974 | if ((!chainp) || | 989 | if ((! chainp) || |
975 | (0 == cert_list_size)) | 990 | (0 == cert_list_size)) |
976 | return GNUNET_SYSERR; | 991 | return GNUNET_SYSERR; |
977 | 992 | ||
978 | size = sizeof(certdn); | 993 | size = sizeof(certdn); |
979 | /* initialize an X.509 certificate structure. */ | 994 | /* initialize an X.509 certificate structure. */ |
980 | gnutls_x509_crt_init(&x509_cert); | 995 | gnutls_x509_crt_init (&x509_cert); |
981 | gnutls_x509_crt_import(x509_cert, | 996 | gnutls_x509_crt_import (x509_cert, |
982 | chainp, | 997 | chainp, |
983 | GNUTLS_X509_FMT_DER); | 998 | GNUTLS_X509_FMT_DER); |
984 | 999 | ||
985 | if (0 != (rc = gnutls_x509_crt_get_dn_by_oid(x509_cert, | 1000 | if (0 != (rc = gnutls_x509_crt_get_dn_by_oid (x509_cert, |
986 | GNUTLS_OID_X520_COMMON_NAME, | 1001 | GNUTLS_OID_X520_COMMON_NAME, |
987 | 0, /* the first and only one */ | 1002 | 0, /* the first and only one */ |
988 | 0 /* no DER encoding */, | 1003 | 0 /* no DER encoding */, |
989 | certdn, | 1004 | certdn, |
990 | &size))) | 1005 | &size))) |
991 | { | 1006 | { |
992 | GNUNET_log(GNUNET_ERROR_TYPE_WARNING, | 1007 | GNUNET_log (GNUNET_ERROR_TYPE_WARNING, |
993 | _("Failed to fetch CN from cert: %s\n"), | 1008 | _ ("Failed to fetch CN from cert: %s\n"), |
994 | gnutls_strerror(rc)); | 1009 | gnutls_strerror (rc)); |
995 | gnutls_x509_crt_deinit(x509_cert); | 1010 | gnutls_x509_crt_deinit (x509_cert); |
996 | return GNUNET_SYSERR; | 1011 | return GNUNET_SYSERR; |
997 | } | 1012 | } |
998 | /* check for TLSA/DANE records */ | 1013 | /* check for TLSA/DANE records */ |
999 | #if HAVE_GNUTLS_DANE | 1014 | #if HAVE_GNUTLS_DANE |
1000 | if (0 != s5r->num_danes) | 1015 | if (0 != s5r->num_danes) |
1001 | { | 1016 | { |
1002 | dane_state_t dane_state; | 1017 | dane_state_t dane_state; |
1003 | dane_query_t dane_query; | 1018 | dane_query_t dane_query; |
1004 | unsigned int verify; | 1019 | unsigned int verify; |
1005 | 1020 | ||
1006 | /* FIXME: add flags to gnutls to NOT read UNBOUND_ROOT_KEY_FILE here! */ | 1021 | /* FIXME: add flags to gnutls to NOT read UNBOUND_ROOT_KEY_FILE here! */ |
1007 | if (0 != (rc = dane_state_init(&dane_state, | 1022 | if (0 != (rc = dane_state_init (&dane_state, |
1008 | #ifdef DANE_F_IGNORE_DNSSEC | 1023 | #ifdef DANE_F_IGNORE_DNSSEC |
1009 | DANE_F_IGNORE_DNSSEC | | 1024 | DANE_F_IGNORE_DNSSEC | |
1010 | #endif | 1025 | #endif |
1011 | DANE_F_IGNORE_LOCAL_RESOLVER))) | 1026 | DANE_F_IGNORE_LOCAL_RESOLVER))) |
1012 | { | 1027 | { |
1013 | GNUNET_log(GNUNET_ERROR_TYPE_WARNING, | 1028 | GNUNET_log (GNUNET_ERROR_TYPE_WARNING, |
1014 | _("Failed to initialize DANE: %s\n"), | 1029 | _ ("Failed to initialize DANE: %s\n"), |
1015 | dane_strerror(rc)); | 1030 | dane_strerror (rc)); |
1016 | gnutls_x509_crt_deinit(x509_cert); | 1031 | gnutls_x509_crt_deinit (x509_cert); |
1017 | return GNUNET_SYSERR; | 1032 | return GNUNET_SYSERR; |
1018 | } | 1033 | } |
1019 | s5r->dane_data[s5r->num_danes] = NULL; | 1034 | s5r->dane_data[s5r->num_danes] = NULL; |
1020 | s5r->dane_data_len[s5r->num_danes] = 0; | 1035 | s5r->dane_data_len[s5r->num_danes] = 0; |
1021 | if (0 != (rc = dane_raw_tlsa(dane_state, | 1036 | if (0 != (rc = dane_raw_tlsa (dane_state, |
1022 | &dane_query, | 1037 | &dane_query, |
1023 | s5r->dane_data, | 1038 | s5r->dane_data, |
1024 | s5r->dane_data_len, | 1039 | s5r->dane_data_len, |
1025 | GNUNET_YES, | 1040 | GNUNET_YES, |
1026 | GNUNET_NO))) | 1041 | GNUNET_NO))) |
1027 | { | 1042 | { |
1028 | GNUNET_log(GNUNET_ERROR_TYPE_WARNING, | 1043 | GNUNET_log (GNUNET_ERROR_TYPE_WARNING, |
1029 | _("Failed to parse DANE record: %s\n"), | 1044 | _ ("Failed to parse DANE record: %s\n"), |
1030 | dane_strerror(rc)); | 1045 | dane_strerror (rc)); |
1031 | dane_state_deinit(dane_state); | 1046 | dane_state_deinit (dane_state); |
1032 | gnutls_x509_crt_deinit(x509_cert); | 1047 | gnutls_x509_crt_deinit (x509_cert); |
1033 | return GNUNET_SYSERR; | 1048 | return GNUNET_SYSERR; |
1034 | } | 1049 | } |
1035 | if (0 != (rc = dane_verify_crt_raw(dane_state, | 1050 | if (0 != (rc = dane_verify_crt_raw (dane_state, |
1036 | chainp, | 1051 | chainp, |
1037 | cert_list_size, | 1052 | cert_list_size, |
1038 | gnutls_certificate_type_get(tlsinfo->internals), | 1053 | gnutls_certificate_type_get ( |
1039 | dane_query, | 1054 | tlsinfo->internals), |
1040 | 0, 0, | 1055 | dane_query, |
1041 | &verify))) | 1056 | 0, 0, |
1042 | { | 1057 | &verify))) |
1043 | GNUNET_log(GNUNET_ERROR_TYPE_WARNING, | 1058 | { |
1044 | _("Failed to verify TLS connection using DANE: %s\n"), | 1059 | GNUNET_log (GNUNET_ERROR_TYPE_WARNING, |
1045 | dane_strerror(rc)); | 1060 | _ ("Failed to verify TLS connection using DANE: %s\n"), |
1046 | dane_query_deinit(dane_query); | 1061 | dane_strerror (rc)); |
1047 | dane_state_deinit(dane_state); | 1062 | dane_query_deinit (dane_query); |
1048 | gnutls_x509_crt_deinit(x509_cert); | 1063 | dane_state_deinit (dane_state); |
1049 | return GNUNET_SYSERR; | 1064 | gnutls_x509_crt_deinit (x509_cert); |
1050 | } | 1065 | return GNUNET_SYSERR; |
1051 | if (0 != verify) | 1066 | } |
1052 | { | 1067 | if (0 != verify) |
1053 | GNUNET_log(GNUNET_ERROR_TYPE_WARNING, | 1068 | { |
1054 | _("Failed DANE verification failed with GnuTLS verify status code: %u\n"), | 1069 | GNUNET_log (GNUNET_ERROR_TYPE_WARNING, |
1055 | verify); | 1070 | _ ( |
1056 | dane_query_deinit(dane_query); | 1071 | "Failed DANE verification failed with GnuTLS verify status code: %u\n"), |
1057 | dane_state_deinit(dane_state); | 1072 | verify); |
1058 | gnutls_x509_crt_deinit(x509_cert); | 1073 | dane_query_deinit (dane_query); |
1059 | return GNUNET_SYSERR; | 1074 | dane_state_deinit (dane_state); |
1060 | } | 1075 | gnutls_x509_crt_deinit (x509_cert); |
1061 | dane_query_deinit(dane_query); | 1076 | return GNUNET_SYSERR; |
1062 | dane_state_deinit(dane_state); | ||
1063 | /* success! */ | ||
1064 | } | 1077 | } |
1078 | dane_query_deinit (dane_query); | ||
1079 | dane_state_deinit (dane_state); | ||
1080 | /* success! */ | ||
1081 | } | ||
1065 | else | 1082 | else |
1066 | #endif | 1083 | #endif |
1067 | { | 1084 | { |
@@ -1070,27 +1087,28 @@ check_ssl_certificate(struct Socks5Request *s5r) | |||
1070 | if (NULL != s5r->leho) | 1087 | if (NULL != s5r->leho) |
1071 | name = s5r->leho; | 1088 | name = s5r->leho; |
1072 | if (NULL != name) | 1089 | if (NULL != name) |
1090 | { | ||
1091 | if (0 == (rc = gnutls_x509_crt_check_hostname (x509_cert, | ||
1092 | name))) | ||
1073 | { | 1093 | { |
1074 | if (0 == (rc = gnutls_x509_crt_check_hostname(x509_cert, | 1094 | GNUNET_log (GNUNET_ERROR_TYPE_WARNING, |
1075 | name))) | 1095 | _ ( |
1076 | { | 1096 | "TLS certificate subject name (%s) does not match `%s': %d\n"), |
1077 | GNUNET_log(GNUNET_ERROR_TYPE_WARNING, | 1097 | certdn, |
1078 | _("TLS certificate subject name (%s) does not match `%s': %d\n"), | 1098 | name, |
1079 | certdn, | 1099 | rc); |
1080 | name, | 1100 | gnutls_x509_crt_deinit (x509_cert); |
1081 | rc); | ||
1082 | gnutls_x509_crt_deinit(x509_cert); | ||
1083 | return GNUNET_SYSERR; | ||
1084 | } | ||
1085 | } | ||
1086 | else | ||
1087 | { | ||
1088 | /* we did not even have the domain name!? */ | ||
1089 | GNUNET_break(0); | ||
1090 | return GNUNET_SYSERR; | 1101 | return GNUNET_SYSERR; |
1091 | } | 1102 | } |
1103 | } | ||
1104 | else | ||
1105 | { | ||
1106 | /* we did not even have the domain name!? */ | ||
1107 | GNUNET_break (0); | ||
1108 | return GNUNET_SYSERR; | ||
1109 | } | ||
1092 | } | 1110 | } |
1093 | gnutls_x509_crt_deinit(x509_cert); | 1111 | gnutls_x509_crt_deinit (x509_cert); |
1094 | return GNUNET_OK; | 1112 | return GNUNET_OK; |
1095 | } | 1113 | } |
1096 | 1114 | ||
@@ -1108,10 +1126,10 @@ check_ssl_certificate(struct Socks5Request *s5r) | |||
1108 | * @return size of processed bytes | 1126 | * @return size of processed bytes |
1109 | */ | 1127 | */ |
1110 | static size_t | 1128 | static size_t |
1111 | curl_check_hdr(void *buffer, | 1129 | curl_check_hdr (void *buffer, |
1112 | size_t size, | 1130 | size_t size, |
1113 | size_t nmemb, | 1131 | size_t nmemb, |
1114 | void *cls) | 1132 | void *cls) |
1115 | { | 1133 | { |
1116 | struct Socks5Request *s5r = cls; | 1134 | struct Socks5Request *s5r = cls; |
1117 | struct HttpResponseHeader *header; | 1135 | struct HttpResponseHeader *header; |
@@ -1127,178 +1145,178 @@ curl_check_hdr(void *buffer, | |||
1127 | int domain_matched; | 1145 | int domain_matched; |
1128 | char *tok; | 1146 | char *tok; |
1129 | 1147 | ||
1130 | GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, | 1148 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
1131 | "Receiving HTTP response header from CURL\n"); | 1149 | "Receiving HTTP response header from CURL\n"); |
1132 | /* first, check TLS certificate */ | 1150 | /* first, check TLS certificate */ |
1133 | if ((GNUNET_YES != s5r->ssl_checked) && | 1151 | if ((GNUNET_YES != s5r->ssl_checked) && |
1134 | (GNUNET_YES == s5r->is_tls)) | 1152 | (GNUNET_YES == s5r->is_tls)) |
1135 | //(HTTPS_PORT == s5r->port)) | 1153 | // (HTTPS_PORT == s5r->port)) |
1136 | { | 1154 | { |
1137 | if (GNUNET_OK != check_ssl_certificate(s5r)) | 1155 | if (GNUNET_OK != check_ssl_certificate (s5r)) |
1138 | return 0; | 1156 | return 0; |
1139 | } | 1157 | } |
1140 | ndup = GNUNET_strndup(buffer, | 1158 | ndup = GNUNET_strndup (buffer, |
1141 | bytes); | 1159 | bytes); |
1142 | hdr_type = strtok(ndup, | 1160 | hdr_type = strtok (ndup, |
1143 | ":"); | 1161 | ":"); |
1144 | if (NULL == hdr_type) | 1162 | if (NULL == hdr_type) |
1145 | { | 1163 | { |
1146 | GNUNET_free(ndup); | 1164 | GNUNET_free (ndup); |
1147 | return bytes; | 1165 | return bytes; |
1148 | } | 1166 | } |
1149 | hdr_val = strtok(NULL, | 1167 | hdr_val = strtok (NULL, |
1150 | ""); | 1168 | ""); |
1151 | if (NULL == hdr_val) | 1169 | if (NULL == hdr_val) |
1152 | { | 1170 | { |
1153 | GNUNET_free(ndup); | 1171 | GNUNET_free (ndup); |
1154 | return bytes; | 1172 | return bytes; |
1155 | } | 1173 | } |
1156 | if (' ' == *hdr_val) | 1174 | if (' ' == *hdr_val) |
1157 | hdr_val++; | 1175 | hdr_val++; |
1158 | 1176 | ||
1159 | /* custom logic for certain header types */ | 1177 | /* custom logic for certain header types */ |
1160 | new_cookie_hdr = NULL; | 1178 | new_cookie_hdr = NULL; |
1161 | if ((NULL != s5r->leho) && | 1179 | if ((NULL != s5r->leho) && |
1162 | (0 == strcasecmp(hdr_type, | 1180 | (0 == strcasecmp (hdr_type, |
1163 | MHD_HTTP_HEADER_SET_COOKIE))) | 1181 | MHD_HTTP_HEADER_SET_COOKIE))) |
1164 | 1182 | ||
1165 | { | 1183 | { |
1166 | new_cookie_hdr = GNUNET_malloc(strlen(hdr_val) + | 1184 | new_cookie_hdr = GNUNET_malloc (strlen (hdr_val) |
1167 | strlen(s5r->domain) + 1); | 1185 | + strlen (s5r->domain) + 1); |
1168 | offset = 0; | 1186 | offset = 0; |
1169 | domain_matched = GNUNET_NO; /* make sure we match domain at most once */ | 1187 | domain_matched = GNUNET_NO; /* make sure we match domain at most once */ |
1170 | for (tok = strtok(hdr_val, ";"); NULL != tok; tok = strtok(NULL, ";")) | 1188 | for (tok = strtok (hdr_val, ";"); NULL != tok; tok = strtok (NULL, ";")) |
1189 | { | ||
1190 | if ((0 == strncasecmp (tok, | ||
1191 | " domain", | ||
1192 | strlen (" domain"))) && | ||
1193 | (GNUNET_NO == domain_matched)) | ||
1194 | { | ||
1195 | domain_matched = GNUNET_YES; | ||
1196 | cookie_domain = tok + strlen (" domain") + 1; | ||
1197 | if (strlen (cookie_domain) < strlen (s5r->leho)) | ||
1171 | { | 1198 | { |
1172 | if ((0 == strncasecmp(tok, | 1199 | delta_cdomain = strlen (s5r->leho) - strlen (cookie_domain); |
1173 | " domain", | 1200 | if (0 == strcasecmp (cookie_domain, |
1174 | strlen(" domain"))) && | 1201 | s5r->leho + delta_cdomain)) |
1175 | (GNUNET_NO == domain_matched)) | 1202 | { |
1176 | { | 1203 | offset += sprintf (new_cookie_hdr + offset, |
1177 | domain_matched = GNUNET_YES; | 1204 | " domain=%s;", |
1178 | cookie_domain = tok + strlen(" domain") + 1; | 1205 | s5r->domain); |
1179 | if (strlen(cookie_domain) < strlen(s5r->leho)) | 1206 | continue; |
1180 | { | 1207 | } |
1181 | delta_cdomain = strlen(s5r->leho) - strlen(cookie_domain); | ||
1182 | if (0 == strcasecmp(cookie_domain, | ||
1183 | s5r->leho + delta_cdomain)) | ||
1184 | { | ||
1185 | offset += sprintf(new_cookie_hdr + offset, | ||
1186 | " domain=%s;", | ||
1187 | s5r->domain); | ||
1188 | continue; | ||
1189 | } | ||
1190 | } | ||
1191 | else if (0 == strcmp(cookie_domain, | ||
1192 | s5r->leho)) | ||
1193 | { | ||
1194 | offset += sprintf(new_cookie_hdr + offset, | ||
1195 | " domain=%s;", | ||
1196 | s5r->domain); | ||
1197 | continue; | ||
1198 | } | ||
1199 | else if (('.' == cookie_domain[0]) && | ||
1200 | (0 == strcmp(&cookie_domain[1], | ||
1201 | s5r->leho))) | ||
1202 | { | ||
1203 | offset += sprintf(new_cookie_hdr + offset, | ||
1204 | " domain=.%s;", | ||
1205 | s5r->domain); | ||
1206 | continue; | ||
1207 | } | ||
1208 | GNUNET_log(GNUNET_ERROR_TYPE_WARNING, | ||
1209 | _("Cookie domain `%s' supplied by server is invalid\n"), | ||
1210 | tok); | ||
1211 | } | ||
1212 | GNUNET_memcpy(new_cookie_hdr + offset, | ||
1213 | tok, | ||
1214 | strlen(tok)); | ||
1215 | offset += strlen(tok); | ||
1216 | new_cookie_hdr[offset++] = ';'; | ||
1217 | } | 1208 | } |
1218 | hdr_val = new_cookie_hdr; | 1209 | else if (0 == strcmp (cookie_domain, |
1219 | } | 1210 | s5r->leho)) |
1220 | |||
1221 | new_location = NULL; | ||
1222 | if (0 == strcasecmp(MHD_HTTP_HEADER_TRANSFER_ENCODING, | ||
1223 | hdr_type)) | ||
1224 | { | ||
1225 | /* Ignore transfer encoding, set automatically by MHD if required */ | ||
1226 | goto cleanup; | ||
1227 | } | ||
1228 | if ((0 == strcasecmp(MHD_HTTP_HEADER_LOCATION, | ||
1229 | hdr_type))) | ||
1230 | { | ||
1231 | char *leho_host; | ||
1232 | |||
1233 | GNUNET_asprintf(&leho_host, | ||
1234 | (GNUNET_YES != s5r->is_tls) //(HTTPS_PORT != s5r->port) | ||
1235 | ? "http://%s" | ||
1236 | : "https://%s", | ||
1237 | s5r->leho); | ||
1238 | if (0 == strncmp(leho_host, | ||
1239 | hdr_val, | ||
1240 | strlen(leho_host))) | ||
1241 | { | 1211 | { |
1242 | GNUNET_asprintf(&new_location, | 1212 | offset += sprintf (new_cookie_hdr + offset, |
1243 | "%s%s%s", | 1213 | " domain=%s;", |
1244 | (GNUNET_YES != s5r->is_tls) //(HTTPS_PORT != s5r->port) | 1214 | s5r->domain); |
1245 | ? "http://" | 1215 | continue; |
1246 | : "https://", | ||
1247 | s5r->domain, | ||
1248 | hdr_val + strlen(leho_host)); | ||
1249 | hdr_val = new_location; | ||
1250 | } | 1216 | } |
1251 | GNUNET_free(leho_host); | 1217 | else if (('.' == cookie_domain[0]) && |
1252 | } | 1218 | (0 == strcmp (&cookie_domain[1], |
1253 | if (0 == strcasecmp(MHD_HTTP_HEADER_ACCESS_CONTROL_ALLOW_ORIGIN, | 1219 | s5r->leho))) |
1254 | hdr_type)) | ||
1255 | { | ||
1256 | char *leho_host; | ||
1257 | |||
1258 | GNUNET_asprintf(&leho_host, | ||
1259 | (GNUNET_YES != s5r->is_tls) //(HTTPS_PORT != s5r->port) | ||
1260 | ? "http://%s" | ||
1261 | : "https://%s", | ||
1262 | s5r->leho); | ||
1263 | if (0 == strncmp(leho_host, | ||
1264 | hdr_val, | ||
1265 | strlen(leho_host))) | ||
1266 | { | 1220 | { |
1267 | GNUNET_asprintf(&new_location, | 1221 | offset += sprintf (new_cookie_hdr + offset, |
1268 | "%s%s", | 1222 | " domain=.%s;", |
1269 | (GNUNET_YES != s5r->is_tls) //(HTTPS_PORT != s5r->port) | 1223 | s5r->domain); |
1270 | ? "http://" | 1224 | continue; |
1271 | : "https://", | ||
1272 | s5r->domain); | ||
1273 | hdr_val = new_location; | ||
1274 | } | 1225 | } |
1275 | GNUNET_free(leho_host); | 1226 | GNUNET_log (GNUNET_ERROR_TYPE_WARNING, |
1227 | _ ("Cookie domain `%s' supplied by server is invalid\n"), | ||
1228 | tok); | ||
1229 | } | ||
1230 | GNUNET_memcpy (new_cookie_hdr + offset, | ||
1231 | tok, | ||
1232 | strlen (tok)); | ||
1233 | offset += strlen (tok); | ||
1234 | new_cookie_hdr[offset++] = ';'; | ||
1276 | } | 1235 | } |
1236 | hdr_val = new_cookie_hdr; | ||
1237 | } | ||
1238 | |||
1239 | new_location = NULL; | ||
1240 | if (0 == strcasecmp (MHD_HTTP_HEADER_TRANSFER_ENCODING, | ||
1241 | hdr_type)) | ||
1242 | { | ||
1243 | /* Ignore transfer encoding, set automatically by MHD if required */ | ||
1244 | goto cleanup; | ||
1245 | } | ||
1246 | if ((0 == strcasecmp (MHD_HTTP_HEADER_LOCATION, | ||
1247 | hdr_type))) | ||
1248 | { | ||
1249 | char *leho_host; | ||
1250 | |||
1251 | GNUNET_asprintf (&leho_host, | ||
1252 | (GNUNET_YES != s5r->is_tls) // (HTTPS_PORT != s5r->port) | ||
1253 | ? "http://%s" | ||
1254 | : "https://%s", | ||
1255 | s5r->leho); | ||
1256 | if (0 == strncmp (leho_host, | ||
1257 | hdr_val, | ||
1258 | strlen (leho_host))) | ||
1259 | { | ||
1260 | GNUNET_asprintf (&new_location, | ||
1261 | "%s%s%s", | ||
1262 | (GNUNET_YES != s5r->is_tls) // (HTTPS_PORT != s5r->port) | ||
1263 | ? "http://" | ||
1264 | : "https://", | ||
1265 | s5r->domain, | ||
1266 | hdr_val + strlen (leho_host)); | ||
1267 | hdr_val = new_location; | ||
1268 | } | ||
1269 | GNUNET_free (leho_host); | ||
1270 | } | ||
1271 | if (0 == strcasecmp (MHD_HTTP_HEADER_ACCESS_CONTROL_ALLOW_ORIGIN, | ||
1272 | hdr_type)) | ||
1273 | { | ||
1274 | char *leho_host; | ||
1275 | |||
1276 | GNUNET_asprintf (&leho_host, | ||
1277 | (GNUNET_YES != s5r->is_tls) // (HTTPS_PORT != s5r->port) | ||
1278 | ? "http://%s" | ||
1279 | : "https://%s", | ||
1280 | s5r->leho); | ||
1281 | if (0 == strncmp (leho_host, | ||
1282 | hdr_val, | ||
1283 | strlen (leho_host))) | ||
1284 | { | ||
1285 | GNUNET_asprintf (&new_location, | ||
1286 | "%s%s", | ||
1287 | (GNUNET_YES != s5r->is_tls) // (HTTPS_PORT != s5r->port) | ||
1288 | ? "http://" | ||
1289 | : "https://", | ||
1290 | s5r->domain); | ||
1291 | hdr_val = new_location; | ||
1292 | } | ||
1293 | GNUNET_free (leho_host); | ||
1294 | } | ||
1277 | 1295 | ||
1278 | /* MHD does not allow certain characters in values, remove those */ | 1296 | /* MHD does not allow certain characters in values, remove those */ |
1279 | if (NULL != (tok = strchr(hdr_val, '\n'))) | 1297 | if (NULL != (tok = strchr (hdr_val, '\n'))) |
1280 | *tok = '\0'; | 1298 | *tok = '\0'; |
1281 | if (NULL != (tok = strchr(hdr_val, '\r'))) | 1299 | if (NULL != (tok = strchr (hdr_val, '\r'))) |
1282 | *tok = '\0'; | 1300 | *tok = '\0'; |
1283 | if (NULL != (tok = strchr(hdr_val, '\t'))) | 1301 | if (NULL != (tok = strchr (hdr_val, '\t'))) |
1284 | *tok = '\0'; | 1302 | *tok = '\0'; |
1285 | if (0 != strlen(hdr_val)) /* Rely in MHD to set those */ | 1303 | if (0 != strlen (hdr_val)) /* Rely in MHD to set those */ |
1286 | { | 1304 | { |
1287 | GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, | 1305 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
1288 | "Adding header %s: %s to MHD response\n", | 1306 | "Adding header %s: %s to MHD response\n", |
1289 | hdr_type, | 1307 | hdr_type, |
1290 | hdr_val); | 1308 | hdr_val); |
1291 | header = GNUNET_new(struct HttpResponseHeader); | 1309 | header = GNUNET_new (struct HttpResponseHeader); |
1292 | header->type = GNUNET_strdup(hdr_type); | 1310 | header->type = GNUNET_strdup (hdr_type); |
1293 | header->value = GNUNET_strdup(hdr_val); | 1311 | header->value = GNUNET_strdup (hdr_val); |
1294 | GNUNET_CONTAINER_DLL_insert(s5r->header_head, | 1312 | GNUNET_CONTAINER_DLL_insert (s5r->header_head, |
1295 | s5r->header_tail, | 1313 | s5r->header_tail, |
1296 | header); | 1314 | header); |
1297 | } | 1315 | } |
1298 | cleanup: | 1316 | cleanup: |
1299 | GNUNET_free(ndup); | 1317 | GNUNET_free (ndup); |
1300 | GNUNET_free_non_null(new_cookie_hdr); | 1318 | GNUNET_free_non_null (new_cookie_hdr); |
1301 | GNUNET_free_non_null(new_location); | 1319 | GNUNET_free_non_null (new_location); |
1302 | return bytes; | 1320 | return bytes; |
1303 | } | 1321 | } |
1304 | 1322 | ||
@@ -1312,73 +1330,73 @@ cleanup: | |||
1312 | * already initialized before | 1330 | * already initialized before |
1313 | */ | 1331 | */ |
1314 | static int | 1332 | static int |
1315 | create_mhd_response_from_s5r(struct Socks5Request *s5r) | 1333 | create_mhd_response_from_s5r (struct Socks5Request *s5r) |
1316 | { | 1334 | { |
1317 | long resp_code; | 1335 | long resp_code; |
1318 | double content_length; | 1336 | double content_length; |
1319 | 1337 | ||
1320 | if (NULL != s5r->response) | 1338 | if (NULL != s5r->response) |
1321 | { | 1339 | { |
1322 | GNUNET_log(GNUNET_ERROR_TYPE_ERROR, | 1340 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, |
1323 | "Response already set!\n"); | 1341 | "Response already set!\n"); |
1324 | return GNUNET_SYSERR; | 1342 | return GNUNET_SYSERR; |
1325 | } | 1343 | } |
1326 | 1344 | ||
1327 | GNUNET_break(CURLE_OK == | 1345 | GNUNET_break (CURLE_OK == |
1328 | curl_easy_getinfo(s5r->curl, | 1346 | curl_easy_getinfo (s5r->curl, |
1329 | CURLINFO_RESPONSE_CODE, | 1347 | CURLINFO_RESPONSE_CODE, |
1330 | &resp_code)); | 1348 | &resp_code)); |
1331 | GNUNET_break(CURLE_OK == | 1349 | GNUNET_break (CURLE_OK == |
1332 | curl_easy_getinfo(s5r->curl, | 1350 | curl_easy_getinfo (s5r->curl, |
1333 | CURLINFO_CONTENT_LENGTH_DOWNLOAD, | 1351 | CURLINFO_CONTENT_LENGTH_DOWNLOAD, |
1334 | &content_length)); | 1352 | &content_length)); |
1335 | GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, | 1353 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
1336 | "Creating MHD response with code %d and size %d for %s%s\n", | 1354 | "Creating MHD response with code %d and size %d for %s%s\n", |
1337 | (int)resp_code, | 1355 | (int) resp_code, |
1338 | (int)content_length, | 1356 | (int) content_length, |
1339 | s5r->domain, | 1357 | s5r->domain, |
1340 | s5r->url); | 1358 | s5r->url); |
1341 | s5r->response_code = resp_code; | 1359 | s5r->response_code = resp_code; |
1342 | s5r->response = MHD_create_response_from_callback((-1 == content_length) | 1360 | s5r->response = MHD_create_response_from_callback ((-1 == content_length) |
1343 | ? MHD_SIZE_UNKNOWN | 1361 | ? MHD_SIZE_UNKNOWN |
1344 | : content_length, | 1362 | : content_length, |
1345 | IO_BUFFERSIZE, | 1363 | IO_BUFFERSIZE, |
1346 | &mhd_content_cb, | 1364 | &mhd_content_cb, |
1347 | s5r, | 1365 | s5r, |
1348 | NULL); | 1366 | NULL); |
1349 | for (struct HttpResponseHeader *header = s5r->header_head; | 1367 | for (struct HttpResponseHeader *header = s5r->header_head; |
1350 | NULL != header; | 1368 | NULL != header; |
1351 | header = header->next) | 1369 | header = header->next) |
1352 | { | 1370 | { |
1353 | if (0 == strcasecmp(header->type, | 1371 | if (0 == strcasecmp (header->type, |
1354 | MHD_HTTP_HEADER_CONTENT_LENGTH)) | 1372 | MHD_HTTP_HEADER_CONTENT_LENGTH)) |
1355 | continue; /* MHD won't let us mess with those, for good reason */ | 1373 | continue; /* MHD won't let us mess with those, for good reason */ |
1356 | if ((0 == strcasecmp(header->type, | 1374 | if ((0 == strcasecmp (header->type, |
1357 | MHD_HTTP_HEADER_TRANSFER_ENCODING)) && | 1375 | MHD_HTTP_HEADER_TRANSFER_ENCODING)) && |
1358 | ((0 == strcasecmp(header->value, | 1376 | ((0 == strcasecmp (header->value, |
1359 | "identity")) || | 1377 | "identity")) || |
1360 | (0 == strcasecmp(header->value, | 1378 | (0 == strcasecmp (header->value, |
1361 | "chunked")))) | 1379 | "chunked")))) |
1362 | continue; /* MHD won't let us mess with those, for good reason */ | 1380 | continue; /* MHD won't let us mess with those, for good reason */ |
1363 | if (MHD_YES != | 1381 | if (MHD_YES != |
1364 | MHD_add_response_header(s5r->response, | 1382 | MHD_add_response_header (s5r->response, |
1365 | header->type, | 1383 | header->type, |
1366 | header->value)) | 1384 | header->value)) |
1367 | { | 1385 | { |
1368 | GNUNET_break(0); | 1386 | GNUNET_break (0); |
1369 | GNUNET_log(GNUNET_ERROR_TYPE_INFO, | 1387 | GNUNET_log (GNUNET_ERROR_TYPE_INFO, |
1370 | "Failed to add header `%s:%s'\n", | 1388 | "Failed to add header `%s:%s'\n", |
1371 | header->type, | 1389 | header->type, |
1372 | header->value); | 1390 | header->value); |
1373 | } | ||
1374 | } | 1391 | } |
1392 | } | ||
1375 | /* force connection to be closed after each request, as we | 1393 | /* force connection to be closed after each request, as we |
1376 | do not support HTTP pipelining (yet, FIXME!) */ | 1394 | do not support HTTP pipelining (yet, FIXME!) */ |
1377 | /*GNUNET_break (MHD_YES == | 1395 | /*GNUNET_break (MHD_YES == |
1378 | MHD_add_response_header (s5r->response, | 1396 | MHD_add_response_header (s5r->response, |
1379 | MHD_HTTP_HEADER_CONNECTION, | 1397 | MHD_HTTP_HEADER_CONNECTION, |
1380 | "close"));*/ | 1398 | "close"));*/ |
1381 | MHD_resume_connection(s5r->con); | 1399 | MHD_resume_connection (s5r->con); |
1382 | s5r->suspended = GNUNET_NO; | 1400 | s5r->suspended = GNUNET_NO; |
1383 | return GNUNET_OK; | 1401 | return GNUNET_OK; |
1384 | } | 1402 | } |
@@ -1395,70 +1413,70 @@ create_mhd_response_from_s5r(struct Socks5Request *s5r) | |||
1395 | * @return number of bytes handled | 1413 | * @return number of bytes handled |
1396 | */ | 1414 | */ |
1397 | static size_t | 1415 | static size_t |
1398 | curl_download_cb(void *ptr, | 1416 | curl_download_cb (void *ptr, |
1399 | size_t size, | 1417 | size_t size, |
1400 | size_t nmemb, | 1418 | size_t nmemb, |
1401 | void* ctx) | 1419 | void*ctx) |
1402 | { | 1420 | { |
1403 | struct Socks5Request *s5r = ctx; | 1421 | struct Socks5Request *s5r = ctx; |
1404 | size_t total = size * nmemb; | 1422 | size_t total = size * nmemb; |
1405 | 1423 | ||
1406 | GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, | 1424 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
1407 | "Receiving %ux%u bytes for `%s%s' from cURL to download\n", | 1425 | "Receiving %ux%u bytes for `%s%s' from cURL to download\n", |
1408 | (unsigned int)size, | 1426 | (unsigned int) size, |
1409 | (unsigned int)nmemb, | 1427 | (unsigned int) nmemb, |
1410 | s5r->domain, | 1428 | s5r->domain, |
1411 | s5r->url); | 1429 | s5r->url); |
1412 | if (NULL == s5r->response) | 1430 | if (NULL == s5r->response) |
1413 | GNUNET_assert(GNUNET_OK == | 1431 | GNUNET_assert (GNUNET_OK == |
1414 | create_mhd_response_from_s5r(s5r)); | 1432 | create_mhd_response_from_s5r (s5r)); |
1415 | if ((SOCKS5_SOCKET_UPLOAD_DONE == s5r->state) && | 1433 | if ((SOCKS5_SOCKET_UPLOAD_DONE == s5r->state) && |
1416 | (0 == s5r->io_len)) | 1434 | (0 == s5r->io_len)) |
1417 | { | 1435 | { |
1418 | GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, | 1436 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
1419 | "Previous upload finished... starting DOWNLOAD.\n"); | 1437 | "Previous upload finished... starting DOWNLOAD.\n"); |
1420 | s5r->state = SOCKS5_SOCKET_DOWNLOAD_STARTED; | 1438 | s5r->state = SOCKS5_SOCKET_DOWNLOAD_STARTED; |
1421 | } | 1439 | } |
1422 | if ((SOCKS5_SOCKET_UPLOAD_STARTED == s5r->state) || | 1440 | if ((SOCKS5_SOCKET_UPLOAD_STARTED == s5r->state) || |
1423 | (SOCKS5_SOCKET_UPLOAD_DONE == s5r->state)) | 1441 | (SOCKS5_SOCKET_UPLOAD_DONE == s5r->state)) |
1424 | { | 1442 | { |
1425 | /* we're still not done with the upload, do not yet | 1443 | /* we're still not done with the upload, do not yet |
1426 | start the download, the IO buffer is still full | 1444 | start the download, the IO buffer is still full |
1427 | with upload data. */ | 1445 | with upload data. */ |
1428 | GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, | 1446 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
1429 | "Pausing CURL download `%s%s', waiting for UPLOAD to finish\n", | 1447 | "Pausing CURL download `%s%s', waiting for UPLOAD to finish\n", |
1430 | s5r->domain, | 1448 | s5r->domain, |
1431 | s5r->url); | 1449 | s5r->url); |
1432 | s5r->curl_paused = GNUNET_YES; | 1450 | s5r->curl_paused = GNUNET_YES; |
1433 | return CURL_WRITEFUNC_PAUSE; /* not yet ready for data download */ | 1451 | return CURL_WRITEFUNC_PAUSE; /* not yet ready for data download */ |
1434 | } | 1452 | } |
1435 | if (sizeof(s5r->io_buf) - s5r->io_len < total) | 1453 | if (sizeof(s5r->io_buf) - s5r->io_len < total) |
1436 | { | 1454 | { |
1437 | GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, | 1455 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
1438 | "Pausing CURL `%s%s' download, not enough space %llu %llu %llu\n", | 1456 | "Pausing CURL `%s%s' download, not enough space %llu %llu %llu\n", |
1439 | s5r->domain, | 1457 | s5r->domain, |
1440 | s5r->url, | 1458 | s5r->url, |
1441 | (unsigned long long)sizeof(s5r->io_buf), | 1459 | (unsigned long long) sizeof(s5r->io_buf), |
1442 | (unsigned long long)s5r->io_len, | 1460 | (unsigned long long) s5r->io_len, |
1443 | (unsigned long long)total); | 1461 | (unsigned long long) total); |
1444 | s5r->curl_paused = GNUNET_YES; | 1462 | s5r->curl_paused = GNUNET_YES; |
1445 | return CURL_WRITEFUNC_PAUSE; /* not enough space */ | 1463 | return CURL_WRITEFUNC_PAUSE; /* not enough space */ |
1446 | } | 1464 | } |
1447 | GNUNET_memcpy(&s5r->io_buf[s5r->io_len], | 1465 | GNUNET_memcpy (&s5r->io_buf[s5r->io_len], |
1448 | ptr, | 1466 | ptr, |
1449 | total); | 1467 | total); |
1450 | s5r->io_len += total; | 1468 | s5r->io_len += total; |
1451 | if (GNUNET_YES == s5r->suspended) | 1469 | if (GNUNET_YES == s5r->suspended) |
1452 | { | 1470 | { |
1453 | MHD_resume_connection(s5r->con); | 1471 | MHD_resume_connection (s5r->con); |
1454 | s5r->suspended = GNUNET_NO; | 1472 | s5r->suspended = GNUNET_NO; |
1455 | } | 1473 | } |
1456 | GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, | 1474 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
1457 | "Received %llu bytes of payload via cURL from %s\n", | 1475 | "Received %llu bytes of payload via cURL from %s\n", |
1458 | (unsigned long long)total, | 1476 | (unsigned long long) total, |
1459 | s5r->domain); | 1477 | s5r->domain); |
1460 | if (s5r->io_len == total) | 1478 | if (s5r->io_len == total) |
1461 | run_mhd_now(s5r->hd); | 1479 | run_mhd_now (s5r->hd); |
1462 | return total; | 1480 | return total; |
1463 | } | 1481 | } |
1464 | 1482 | ||
@@ -1474,64 +1492,64 @@ curl_download_cb(void *ptr, | |||
1474 | * @return number of bytes copied to @a buf | 1492 | * @return number of bytes copied to @a buf |
1475 | */ | 1493 | */ |
1476 | static size_t | 1494 | static size_t |
1477 | curl_upload_cb(void *buf, | 1495 | curl_upload_cb (void *buf, |
1478 | size_t size, | 1496 | size_t size, |
1479 | size_t nmemb, | 1497 | size_t nmemb, |
1480 | void *cls) | 1498 | void *cls) |
1481 | { | 1499 | { |
1482 | struct Socks5Request *s5r = cls; | 1500 | struct Socks5Request *s5r = cls; |
1483 | size_t len = size * nmemb; | 1501 | size_t len = size * nmemb; |
1484 | size_t to_copy; | 1502 | size_t to_copy; |
1485 | 1503 | ||
1486 | GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, | 1504 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
1487 | "Receiving %ux%u bytes for `%s%s' from cURL to upload\n", | 1505 | "Receiving %ux%u bytes for `%s%s' from cURL to upload\n", |
1488 | (unsigned int)size, | 1506 | (unsigned int) size, |
1489 | (unsigned int)nmemb, | 1507 | (unsigned int) nmemb, |
1490 | s5r->domain, | 1508 | s5r->domain, |
1491 | s5r->url); | 1509 | s5r->url); |
1492 | 1510 | ||
1493 | if ((0 == s5r->io_len) && | 1511 | if ((0 == s5r->io_len) && |
1494 | (SOCKS5_SOCKET_UPLOAD_DONE != s5r->state)) | 1512 | (SOCKS5_SOCKET_UPLOAD_DONE != s5r->state)) |
1495 | { | 1513 | { |
1496 | GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, | 1514 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
1497 | "Pausing CURL UPLOAD %s%s, need more data\n", | 1515 | "Pausing CURL UPLOAD %s%s, need more data\n", |
1498 | s5r->domain, | 1516 | s5r->domain, |
1499 | s5r->url); | 1517 | s5r->url); |
1500 | return CURL_READFUNC_PAUSE; | 1518 | return CURL_READFUNC_PAUSE; |
1501 | } | 1519 | } |
1502 | if ((0 == s5r->io_len) && | 1520 | if ((0 == s5r->io_len) && |
1503 | (SOCKS5_SOCKET_UPLOAD_DONE == s5r->state)) | 1521 | (SOCKS5_SOCKET_UPLOAD_DONE == s5r->state)) |
1522 | { | ||
1523 | s5r->state = SOCKS5_SOCKET_DOWNLOAD_STARTED; | ||
1524 | if (GNUNET_YES == s5r->curl_paused) | ||
1504 | { | 1525 | { |
1505 | s5r->state = SOCKS5_SOCKET_DOWNLOAD_STARTED; | 1526 | s5r->curl_paused = GNUNET_NO; |
1506 | if (GNUNET_YES == s5r->curl_paused) | 1527 | curl_easy_pause (s5r->curl, |
1507 | { | 1528 | CURLPAUSE_CONT); |
1508 | s5r->curl_paused = GNUNET_NO; | 1529 | } |
1509 | curl_easy_pause(s5r->curl, | 1530 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
1510 | CURLPAUSE_CONT); | 1531 | "Completed CURL UPLOAD %s%s\n", |
1511 | } | 1532 | s5r->domain, |
1512 | GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, | 1533 | s5r->url); |
1513 | "Completed CURL UPLOAD %s%s\n", | 1534 | return 0; /* upload finished, can now download */ |
1514 | s5r->domain, | 1535 | } |
1515 | s5r->url); | ||
1516 | return 0; /* upload finished, can now download */ | ||
1517 | } | ||
1518 | if ((SOCKS5_SOCKET_UPLOAD_STARTED != s5r->state) && | 1536 | if ((SOCKS5_SOCKET_UPLOAD_STARTED != s5r->state) && |
1519 | (SOCKS5_SOCKET_UPLOAD_DONE != s5r->state)) | 1537 | (SOCKS5_SOCKET_UPLOAD_DONE != s5r->state)) |
1520 | { | 1538 | { |
1521 | GNUNET_break(0); | 1539 | GNUNET_break (0); |
1522 | return CURL_READFUNC_ABORT; | 1540 | return CURL_READFUNC_ABORT; |
1523 | } | 1541 | } |
1524 | to_copy = GNUNET_MIN(s5r->io_len, | 1542 | to_copy = GNUNET_MIN (s5r->io_len, |
1525 | len); | 1543 | len); |
1526 | GNUNET_memcpy(buf, | 1544 | GNUNET_memcpy (buf, |
1527 | s5r->io_buf, | 1545 | s5r->io_buf, |
1528 | to_copy); | 1546 | to_copy); |
1529 | memmove(s5r->io_buf, | 1547 | memmove (s5r->io_buf, |
1530 | &s5r->io_buf[to_copy], | 1548 | &s5r->io_buf[to_copy], |
1531 | s5r->io_len - to_copy); | 1549 | s5r->io_len - to_copy); |
1532 | s5r->io_len -= to_copy; | 1550 | s5r->io_len -= to_copy; |
1533 | if (s5r->io_len + to_copy == sizeof(s5r->io_buf)) | 1551 | if (s5r->io_len + to_copy == sizeof(s5r->io_buf)) |
1534 | run_mhd_now(s5r->hd); /* got more space for upload now */ | 1552 | run_mhd_now (s5r->hd); /* got more space for upload now */ |
1535 | return to_copy; | 1553 | return to_copy; |
1536 | } | 1554 | } |
1537 | 1555 | ||
@@ -1546,14 +1564,14 @@ curl_upload_cb(void *buf, | |||
1546 | * @param cls closure | 1564 | * @param cls closure |
1547 | */ | 1565 | */ |
1548 | static void | 1566 | static void |
1549 | curl_task_download(void *cls); | 1567 | curl_task_download (void *cls); |
1550 | 1568 | ||
1551 | 1569 | ||
1552 | /** | 1570 | /** |
1553 | * Ask cURL for the select() sets and schedule cURL operations. | 1571 | * Ask cURL for the select() sets and schedule cURL operations. |
1554 | */ | 1572 | */ |
1555 | static void | 1573 | static void |
1556 | curl_download_prepare() | 1574 | curl_download_prepare () |
1557 | { | 1575 | { |
1558 | CURLMcode mret; | 1576 | CURLMcode mret; |
1559 | fd_set rs; | 1577 | fd_set rs; |
@@ -1565,63 +1583,64 @@ curl_download_prepare() | |||
1565 | long to; | 1583 | long to; |
1566 | struct GNUNET_TIME_Relative rtime; | 1584 | struct GNUNET_TIME_Relative rtime; |
1567 | 1585 | ||
1568 | GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, | 1586 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
1569 | "Scheduling CURL interaction\n"); | 1587 | "Scheduling CURL interaction\n"); |
1570 | if (NULL != curl_download_task) | 1588 | if (NULL != curl_download_task) |
1571 | { | 1589 | { |
1572 | GNUNET_SCHEDULER_cancel(curl_download_task); | 1590 | GNUNET_SCHEDULER_cancel (curl_download_task); |
1573 | curl_download_task = NULL; | 1591 | curl_download_task = NULL; |
1574 | } | 1592 | } |
1575 | max = -1; | 1593 | max = -1; |
1576 | FD_ZERO(&rs); | 1594 | FD_ZERO (&rs); |
1577 | FD_ZERO(&ws); | 1595 | FD_ZERO (&ws); |
1578 | FD_ZERO(&es); | 1596 | FD_ZERO (&es); |
1579 | if (CURLM_OK != (mret = curl_multi_fdset(curl_multi, | 1597 | if (CURLM_OK != (mret = curl_multi_fdset (curl_multi, |
1580 | &rs, | 1598 | &rs, |
1581 | &ws, | 1599 | &ws, |
1582 | &es, | 1600 | &es, |
1583 | &max))) | 1601 | &max))) |
1584 | { | 1602 | { |
1585 | GNUNET_log(GNUNET_ERROR_TYPE_ERROR, | 1603 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, |
1586 | "%s failed at %s:%d: `%s'\n", | 1604 | "%s failed at %s:%d: `%s'\n", |
1587 | "curl_multi_fdset", __FILE__, __LINE__, | 1605 | "curl_multi_fdset", __FILE__, __LINE__, |
1588 | curl_multi_strerror(mret)); | 1606 | curl_multi_strerror (mret)); |
1589 | return; | 1607 | return; |
1590 | } | 1608 | } |
1591 | to = -1; | 1609 | to = -1; |
1592 | GNUNET_break(CURLM_OK == | 1610 | GNUNET_break (CURLM_OK == |
1593 | curl_multi_timeout(curl_multi, | 1611 | curl_multi_timeout (curl_multi, |
1594 | &to)); | 1612 | &to)); |
1595 | if (-1 == to) | 1613 | if (-1 == to) |
1596 | rtime = GNUNET_TIME_UNIT_FOREVER_REL; | 1614 | rtime = GNUNET_TIME_UNIT_FOREVER_REL; |
1597 | else | 1615 | else |
1598 | rtime = GNUNET_TIME_relative_multiply(GNUNET_TIME_UNIT_MILLISECONDS, | 1616 | rtime = GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MILLISECONDS, |
1599 | to); | 1617 | to); |
1600 | if (-1 != max) | 1618 | if (-1 != max) |
1601 | { | 1619 | { |
1602 | grs = GNUNET_NETWORK_fdset_create(); | 1620 | grs = GNUNET_NETWORK_fdset_create (); |
1603 | gws = GNUNET_NETWORK_fdset_create(); | 1621 | gws = GNUNET_NETWORK_fdset_create (); |
1604 | GNUNET_NETWORK_fdset_copy_native(grs, | 1622 | GNUNET_NETWORK_fdset_copy_native (grs, |
1605 | &rs, | 1623 | &rs, |
1606 | max + 1); | 1624 | max + 1); |
1607 | GNUNET_NETWORK_fdset_copy_native(gws, | 1625 | GNUNET_NETWORK_fdset_copy_native (gws, |
1608 | &ws, | 1626 | &ws, |
1609 | max + 1); | 1627 | max + 1); |
1610 | curl_download_task = GNUNET_SCHEDULER_add_select(GNUNET_SCHEDULER_PRIORITY_DEFAULT, | 1628 | curl_download_task = GNUNET_SCHEDULER_add_select ( |
1611 | rtime, | 1629 | GNUNET_SCHEDULER_PRIORITY_DEFAULT, |
1612 | grs, | 1630 | rtime, |
1613 | gws, | 1631 | grs, |
1632 | gws, | ||
1633 | &curl_task_download, | ||
1634 | curl_multi); | ||
1635 | GNUNET_NETWORK_fdset_destroy (gws); | ||
1636 | GNUNET_NETWORK_fdset_destroy (grs); | ||
1637 | } | ||
1638 | else | ||
1639 | { | ||
1640 | curl_download_task = GNUNET_SCHEDULER_add_delayed (rtime, | ||
1614 | &curl_task_download, | 1641 | &curl_task_download, |
1615 | curl_multi); | 1642 | curl_multi); |
1616 | GNUNET_NETWORK_fdset_destroy(gws); | 1643 | } |
1617 | GNUNET_NETWORK_fdset_destroy(grs); | ||
1618 | } | ||
1619 | else | ||
1620 | { | ||
1621 | curl_download_task = GNUNET_SCHEDULER_add_delayed(rtime, | ||
1622 | &curl_task_download, | ||
1623 | curl_multi); | ||
1624 | } | ||
1625 | } | 1644 | } |
1626 | 1645 | ||
1627 | 1646 | ||
@@ -1631,7 +1650,7 @@ curl_download_prepare() | |||
1631 | * @param cls closure, NULL | 1650 | * @param cls closure, NULL |
1632 | */ | 1651 | */ |
1633 | static void | 1652 | static void |
1634 | curl_task_download(void *cls) | 1653 | curl_task_download (void *cls) |
1635 | { | 1654 | { |
1636 | int running; | 1655 | int running; |
1637 | int msgnum; | 1656 | int msgnum; |
@@ -1640,109 +1659,109 @@ curl_task_download(void *cls) | |||
1640 | struct Socks5Request *s5r; | 1659 | struct Socks5Request *s5r; |
1641 | 1660 | ||
1642 | curl_download_task = NULL; | 1661 | curl_download_task = NULL; |
1643 | GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, | 1662 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
1644 | "Running CURL interaction\n"); | 1663 | "Running CURL interaction\n"); |
1645 | do | 1664 | do |
1646 | { | 1665 | { |
1647 | running = 0; | 1666 | running = 0; |
1648 | mret = curl_multi_perform(curl_multi, | 1667 | mret = curl_multi_perform (curl_multi, |
1649 | &running); | 1668 | &running); |
1650 | GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, | 1669 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
1651 | "Checking CURL multi status: %d\n", | 1670 | "Checking CURL multi status: %d\n", |
1652 | mret); | 1671 | mret); |
1653 | while (NULL != (msg = curl_multi_info_read(curl_multi, | 1672 | while (NULL != (msg = curl_multi_info_read (curl_multi, |
1654 | &msgnum))) | 1673 | &msgnum))) |
1674 | { | ||
1675 | GNUNET_break (CURLE_OK == | ||
1676 | curl_easy_getinfo (msg->easy_handle, | ||
1677 | CURLINFO_PRIVATE, | ||
1678 | (char **) &s5r)); | ||
1679 | if (NULL == s5r) | ||
1680 | { | ||
1681 | GNUNET_break (0); | ||
1682 | continue; | ||
1683 | } | ||
1684 | switch (msg->msg) | ||
1685 | { | ||
1686 | case CURLMSG_NONE: | ||
1687 | /* documentation says this is not used */ | ||
1688 | GNUNET_break (0); | ||
1689 | break; | ||
1690 | |||
1691 | case CURLMSG_DONE: | ||
1692 | switch (msg->data.result) | ||
1655 | { | 1693 | { |
1656 | GNUNET_break(CURLE_OK == | 1694 | case CURLE_OK: |
1657 | curl_easy_getinfo(msg->easy_handle, | 1695 | case CURLE_GOT_NOTHING: |
1658 | CURLINFO_PRIVATE, | 1696 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
1659 | (char **)&s5r)); | 1697 | "CURL download %s%s completed.\n", |
1660 | if (NULL == s5r) | 1698 | s5r->domain, |
1661 | { | 1699 | s5r->url); |
1662 | GNUNET_break(0); | 1700 | if (NULL == s5r->response) |
1663 | continue; | 1701 | { |
1664 | } | 1702 | GNUNET_assert (GNUNET_OK == |
1665 | switch (msg->msg) | 1703 | create_mhd_response_from_s5r (s5r)); |
1666 | { | 1704 | } |
1667 | case CURLMSG_NONE: | 1705 | s5r->state = SOCKS5_SOCKET_DOWNLOAD_DONE; |
1668 | /* documentation says this is not used */ | 1706 | if (GNUNET_YES == s5r->suspended) |
1669 | GNUNET_break(0); | 1707 | { |
1670 | break; | 1708 | MHD_resume_connection (s5r->con); |
1671 | 1709 | s5r->suspended = GNUNET_NO; | |
1672 | case CURLMSG_DONE: | 1710 | } |
1673 | switch (msg->data.result) | 1711 | run_mhd_now (s5r->hd); |
1674 | { | 1712 | break; |
1675 | case CURLE_OK: | 1713 | |
1676 | case CURLE_GOT_NOTHING: | 1714 | default: |
1677 | GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, | 1715 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, |
1678 | "CURL download %s%s completed.\n", | 1716 | "Download curl %s%s failed: %s\n", |
1679 | s5r->domain, | 1717 | s5r->domain, |
1680 | s5r->url); | 1718 | s5r->url, |
1681 | if (NULL == s5r->response) | 1719 | curl_easy_strerror (msg->data.result)); |
1682 | { | 1720 | /* FIXME: indicate error somehow? close MHD connection badly as well? */ |
1683 | GNUNET_assert(GNUNET_OK == | 1721 | s5r->state = SOCKS5_SOCKET_DOWNLOAD_DONE; |
1684 | create_mhd_response_from_s5r(s5r)); | 1722 | if (GNUNET_YES == s5r->suspended) |
1685 | } | 1723 | { |
1686 | s5r->state = SOCKS5_SOCKET_DOWNLOAD_DONE; | 1724 | MHD_resume_connection (s5r->con); |
1687 | if (GNUNET_YES == s5r->suspended) | 1725 | s5r->suspended = GNUNET_NO; |
1688 | { | 1726 | } |
1689 | MHD_resume_connection(s5r->con); | 1727 | run_mhd_now (s5r->hd); |
1690 | s5r->suspended = GNUNET_NO; | 1728 | break; |
1691 | } | ||
1692 | run_mhd_now(s5r->hd); | ||
1693 | break; | ||
1694 | |||
1695 | default: | ||
1696 | GNUNET_log(GNUNET_ERROR_TYPE_ERROR, | ||
1697 | "Download curl %s%s failed: %s\n", | ||
1698 | s5r->domain, | ||
1699 | s5r->url, | ||
1700 | curl_easy_strerror(msg->data.result)); | ||
1701 | /* FIXME: indicate error somehow? close MHD connection badly as well? */ | ||
1702 | s5r->state = SOCKS5_SOCKET_DOWNLOAD_DONE; | ||
1703 | if (GNUNET_YES == s5r->suspended) | ||
1704 | { | ||
1705 | MHD_resume_connection(s5r->con); | ||
1706 | s5r->suspended = GNUNET_NO; | ||
1707 | } | ||
1708 | run_mhd_now(s5r->hd); | ||
1709 | break; | ||
1710 | } | ||
1711 | if (NULL == s5r->response) | ||
1712 | s5r->response = curl_failure_response; | ||
1713 | break; | ||
1714 | |||
1715 | case CURLMSG_LAST: | ||
1716 | /* documentation says this is not used */ | ||
1717 | GNUNET_break(0); | ||
1718 | break; | ||
1719 | |||
1720 | default: | ||
1721 | /* unexpected status code */ | ||
1722 | GNUNET_break(0); | ||
1723 | break; | ||
1724 | } | ||
1725 | } | 1729 | } |
1726 | ; | 1730 | if (NULL == s5r->response) |
1731 | s5r->response = curl_failure_response; | ||
1732 | break; | ||
1733 | |||
1734 | case CURLMSG_LAST: | ||
1735 | /* documentation says this is not used */ | ||
1736 | GNUNET_break (0); | ||
1737 | break; | ||
1738 | |||
1739 | default: | ||
1740 | /* unexpected status code */ | ||
1741 | GNUNET_break (0); | ||
1742 | break; | ||
1743 | } | ||
1727 | } | 1744 | } |
1745 | ; | ||
1746 | } | ||
1728 | while (mret == CURLM_CALL_MULTI_PERFORM); | 1747 | while (mret == CURLM_CALL_MULTI_PERFORM); |
1729 | if (CURLM_OK != mret) | 1748 | if (CURLM_OK != mret) |
1730 | GNUNET_log(GNUNET_ERROR_TYPE_ERROR, | 1749 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, |
1731 | "%s failed at %s:%d: `%s'\n", | 1750 | "%s failed at %s:%d: `%s'\n", |
1732 | "curl_multi_perform", __FILE__, __LINE__, | 1751 | "curl_multi_perform", __FILE__, __LINE__, |
1733 | curl_multi_strerror(mret)); | 1752 | curl_multi_strerror (mret)); |
1734 | if (0 == running) | 1753 | if (0 == running) |
1754 | { | ||
1755 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
1756 | "Suspending cURL multi loop, no more events pending\n"); | ||
1757 | if (NULL != curl_download_task) | ||
1735 | { | 1758 | { |
1736 | GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, | 1759 | GNUNET_SCHEDULER_cancel (curl_download_task); |
1737 | "Suspending cURL multi loop, no more events pending\n"); | 1760 | curl_download_task = NULL; |
1738 | if (NULL != curl_download_task) | ||
1739 | { | ||
1740 | GNUNET_SCHEDULER_cancel(curl_download_task); | ||
1741 | curl_download_task = NULL; | ||
1742 | } | ||
1743 | return; /* nothing more in progress */ | ||
1744 | } | 1761 | } |
1745 | curl_download_prepare(); | 1762 | return; /* nothing more in progress */ |
1763 | } | ||
1764 | curl_download_prepare (); | ||
1746 | } | 1765 | } |
1747 | 1766 | ||
1748 | 1767 | ||
@@ -1763,28 +1782,28 @@ curl_task_download(void *cls) | |||
1763 | * @return #MHD_YES to continue to iterate | 1782 | * @return #MHD_YES to continue to iterate |
1764 | */ | 1783 | */ |
1765 | static int | 1784 | static int |
1766 | con_val_iter(void *cls, | 1785 | con_val_iter (void *cls, |
1767 | enum MHD_ValueKind kind, | 1786 | enum MHD_ValueKind kind, |
1768 | const char *key, | 1787 | const char *key, |
1769 | const char *value) | 1788 | const char *value) |
1770 | { | 1789 | { |
1771 | struct Socks5Request *s5r = cls; | 1790 | struct Socks5Request *s5r = cls; |
1772 | char *hdr; | 1791 | char *hdr; |
1773 | 1792 | ||
1774 | if ((0 == strcasecmp(MHD_HTTP_HEADER_HOST, | 1793 | if ((0 == strcasecmp (MHD_HTTP_HEADER_HOST, |
1775 | key)) && | 1794 | key)) && |
1776 | (NULL != s5r->leho)) | 1795 | (NULL != s5r->leho)) |
1777 | value = s5r->leho; | 1796 | value = s5r->leho; |
1778 | GNUNET_asprintf(&hdr, | 1797 | GNUNET_asprintf (&hdr, |
1779 | "%s: %s", | 1798 | "%s: %s", |
1780 | key, | 1799 | key, |
1781 | value); | 1800 | value); |
1782 | GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, | 1801 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
1783 | "Adding HEADER `%s' to HTTP request\n", | 1802 | "Adding HEADER `%s' to HTTP request\n", |
1784 | hdr); | 1803 | hdr); |
1785 | s5r->headers = curl_slist_append(s5r->headers, | 1804 | s5r->headers = curl_slist_append (s5r->headers, |
1786 | hdr); | 1805 | hdr); |
1787 | GNUNET_free(hdr); | 1806 | GNUNET_free (hdr); |
1788 | return MHD_YES; | 1807 | return MHD_YES; |
1789 | } | 1808 | } |
1790 | 1809 | ||
@@ -1813,14 +1832,14 @@ con_val_iter(void *cls, | |||
1813 | * error while handling the request | 1832 | * error while handling the request |
1814 | */ | 1833 | */ |
1815 | static int | 1834 | static int |
1816 | create_response(void *cls, | 1835 | create_response (void *cls, |
1817 | struct MHD_Connection *con, | 1836 | struct MHD_Connection *con, |
1818 | const char *url, | 1837 | const char *url, |
1819 | const char *meth, | 1838 | const char *meth, |
1820 | const char *ver, | 1839 | const char *ver, |
1821 | const char *upload_data, | 1840 | const char *upload_data, |
1822 | size_t *upload_data_size, | 1841 | size_t *upload_data_size, |
1823 | void **con_cls) | 1842 | void **con_cls) |
1824 | { | 1843 | { |
1825 | struct Socks5Request *s5r = *con_cls; | 1844 | struct Socks5Request *s5r = *con_cls; |
1826 | char *curlurl; | 1845 | char *curlurl; |
@@ -1833,415 +1852,415 @@ create_response(void *cls, | |||
1833 | size_t left; | 1852 | size_t left; |
1834 | 1853 | ||
1835 | if (NULL == s5r) | 1854 | if (NULL == s5r) |
1836 | { | 1855 | { |
1837 | GNUNET_break(0); | 1856 | GNUNET_break (0); |
1838 | return MHD_NO; | 1857 | return MHD_NO; |
1839 | } | 1858 | } |
1840 | s5r->con = con; | 1859 | s5r->con = con; |
1841 | /* Fresh connection. */ | 1860 | /* Fresh connection. */ |
1842 | if (SOCKS5_SOCKET_WITH_MHD == s5r->state) | 1861 | if (SOCKS5_SOCKET_WITH_MHD == s5r->state) |
1862 | { | ||
1863 | /* first time here, initialize curl handle */ | ||
1864 | if (s5r->is_gns) | ||
1843 | { | 1865 | { |
1844 | /* first time here, initialize curl handle */ | 1866 | sa = (const struct sockaddr *) &s5r->destination_address; |
1845 | if (s5r->is_gns) | 1867 | switch (sa->sa_family) |
1846 | { | 1868 | { |
1847 | sa = (const struct sockaddr *)&s5r->destination_address; | 1869 | case AF_INET: |
1848 | switch (sa->sa_family) | 1870 | s4 = (const struct sockaddr_in *) &s5r->destination_address; |
1849 | { | 1871 | if (NULL == inet_ntop (AF_INET, |
1850 | case AF_INET: | 1872 | &s4->sin_addr, |
1851 | s4 = (const struct sockaddr_in *)&s5r->destination_address; | 1873 | ipstring, |
1852 | if (NULL == inet_ntop(AF_INET, | 1874 | sizeof(ipstring))) |
1853 | &s4->sin_addr, | ||
1854 | ipstring, | ||
1855 | sizeof(ipstring))) | ||
1856 | { | ||
1857 | GNUNET_break(0); | ||
1858 | return MHD_NO; | ||
1859 | } | ||
1860 | GNUNET_snprintf(ipaddr, | ||
1861 | sizeof(ipaddr), | ||
1862 | "%s", | ||
1863 | ipstring); | ||
1864 | port = ntohs(s4->sin_port); | ||
1865 | break; | ||
1866 | |||
1867 | case AF_INET6: | ||
1868 | s6 = (const struct sockaddr_in6 *)&s5r->destination_address; | ||
1869 | if (NULL == inet_ntop(AF_INET6, | ||
1870 | &s6->sin6_addr, | ||
1871 | ipstring, | ||
1872 | sizeof(ipstring))) | ||
1873 | { | ||
1874 | GNUNET_break(0); | ||
1875 | return MHD_NO; | ||
1876 | } | ||
1877 | GNUNET_snprintf(ipaddr, | ||
1878 | sizeof(ipaddr), | ||
1879 | "%s", | ||
1880 | ipstring); | ||
1881 | port = ntohs(s6->sin6_port); | ||
1882 | break; | ||
1883 | |||
1884 | default: | ||
1885 | GNUNET_break(0); | ||
1886 | return MHD_NO; | ||
1887 | } | ||
1888 | } | ||
1889 | else | ||
1890 | { | ||
1891 | port = s5r->port; | ||
1892 | } | ||
1893 | if (NULL == s5r->curl) | ||
1894 | s5r->curl = curl_easy_init(); | ||
1895 | if (NULL == s5r->curl) | ||
1896 | return MHD_queue_response(con, | ||
1897 | MHD_HTTP_INTERNAL_SERVER_ERROR, | ||
1898 | curl_failure_response); | ||
1899 | curl_easy_setopt(s5r->curl, | ||
1900 | CURLOPT_HEADERFUNCTION, | ||
1901 | &curl_check_hdr); | ||
1902 | curl_easy_setopt(s5r->curl, | ||
1903 | CURLOPT_HEADERDATA, | ||
1904 | s5r); | ||
1905 | curl_easy_setopt(s5r->curl, | ||
1906 | CURLOPT_FOLLOWLOCATION, | ||
1907 | 0); | ||
1908 | if (s5r->is_gns) | ||
1909 | curl_easy_setopt(s5r->curl, | ||
1910 | CURLOPT_IPRESOLVE, | ||
1911 | CURL_IPRESOLVE_V4); | ||
1912 | curl_easy_setopt(s5r->curl, | ||
1913 | CURLOPT_CONNECTTIMEOUT, | ||
1914 | 600L); | ||
1915 | curl_easy_setopt(s5r->curl, | ||
1916 | CURLOPT_TIMEOUT, | ||
1917 | 600L); | ||
1918 | curl_easy_setopt(s5r->curl, | ||
1919 | CURLOPT_NOSIGNAL, | ||
1920 | 1L); | ||
1921 | curl_easy_setopt(s5r->curl, | ||
1922 | CURLOPT_HTTP_CONTENT_DECODING, | ||
1923 | 0); | ||
1924 | curl_easy_setopt(s5r->curl, | ||
1925 | CURLOPT_NOSIGNAL, | ||
1926 | 1L); | ||
1927 | curl_easy_setopt(s5r->curl, | ||
1928 | CURLOPT_PRIVATE, | ||
1929 | s5r); | ||
1930 | curl_easy_setopt(s5r->curl, | ||
1931 | CURLOPT_VERBOSE, | ||
1932 | 0L); | ||
1933 | /** | ||
1934 | * Pre-populate cache to resolve Hostname. | ||
1935 | * This is necessary as the DNS name in the CURLOPT_URL is used | ||
1936 | * for SNI http://de.wikipedia.org/wiki/Server_Name_Indication | ||
1937 | */ | ||
1938 | if (NULL != s5r->leho) | ||
1939 | { | ||
1940 | char *curl_hosts; | ||
1941 | |||
1942 | GNUNET_asprintf(&curl_hosts, | ||
1943 | "%s:%d:%s", | ||
1944 | s5r->leho, | ||
1945 | port, | ||
1946 | ipaddr); | ||
1947 | s5r->hosts = curl_slist_append(NULL, | ||
1948 | curl_hosts); | ||
1949 | curl_easy_setopt(s5r->curl, | ||
1950 | CURLOPT_RESOLVE, | ||
1951 | s5r->hosts); | ||
1952 | GNUNET_free(curl_hosts); | ||
1953 | } | ||
1954 | if (s5r->is_gns) | ||
1955 | { | ||
1956 | GNUNET_asprintf(&curlurl, | ||
1957 | (GNUNET_YES != s5r->is_tls) //(HTTPS_PORT != s5r->port) | ||
1958 | ? "http://%s:%d%s" | ||
1959 | : "https://%s:%d%s", | ||
1960 | (NULL != s5r->leho) | ||
1961 | ? s5r->leho | ||
1962 | : ipaddr, | ||
1963 | port, | ||
1964 | s5r->url); | ||
1965 | } | ||
1966 | else | ||
1967 | { | ||
1968 | GNUNET_asprintf(&curlurl, | ||
1969 | (GNUNET_YES != s5r->is_tls) //(HTTPS_PORT != s5r->port) | ||
1970 | ? "http://%s:%d%s" | ||
1971 | : "https://%s:%d%s", | ||
1972 | s5r->domain, | ||
1973 | port, | ||
1974 | s5r->url); | ||
1975 | } | ||
1976 | curl_easy_setopt(s5r->curl, | ||
1977 | CURLOPT_URL, | ||
1978 | curlurl); | ||
1979 | GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, | ||
1980 | "Launching %s CURL interaction, fetching `%s'\n", | ||
1981 | (s5r->is_gns) ? "GNS" : "DNS", | ||
1982 | curlurl); | ||
1983 | GNUNET_free(curlurl); | ||
1984 | if (0 == strcasecmp(meth, | ||
1985 | MHD_HTTP_METHOD_PUT)) | ||
1986 | { | ||
1987 | s5r->state = SOCKS5_SOCKET_UPLOAD_STARTED; | ||
1988 | curl_easy_setopt(s5r->curl, | ||
1989 | CURLOPT_UPLOAD, | ||
1990 | 1L); | ||
1991 | curl_easy_setopt(s5r->curl, | ||
1992 | CURLOPT_WRITEFUNCTION, | ||
1993 | &curl_download_cb); | ||
1994 | curl_easy_setopt(s5r->curl, | ||
1995 | CURLOPT_WRITEDATA, | ||
1996 | s5r); | ||
1997 | GNUNET_assert(CURLE_OK == | ||
1998 | curl_easy_setopt(s5r->curl, | ||
1999 | CURLOPT_READFUNCTION, | ||
2000 | &curl_upload_cb)); | ||
2001 | curl_easy_setopt(s5r->curl, | ||
2002 | CURLOPT_READDATA, | ||
2003 | s5r); | ||
2004 | { | ||
2005 | const char *us; | ||
2006 | long upload_size = 0; | ||
2007 | |||
2008 | us = MHD_lookup_connection_value(con, | ||
2009 | MHD_HEADER_KIND, | ||
2010 | MHD_HTTP_HEADER_CONTENT_LENGTH); | ||
2011 | if ((1 == sscanf(us, | ||
2012 | "%ld", | ||
2013 | &upload_size)) && | ||
2014 | (upload_size >= 0)) | ||
2015 | { | ||
2016 | curl_easy_setopt(s5r->curl, | ||
2017 | CURLOPT_INFILESIZE, | ||
2018 | upload_size); | ||
2019 | } | ||
2020 | } | ||
2021 | } | ||
2022 | else if (0 == strcasecmp(meth, MHD_HTTP_METHOD_POST)) | ||
2023 | { | ||
2024 | s5r->state = SOCKS5_SOCKET_UPLOAD_STARTED; | ||
2025 | curl_easy_setopt(s5r->curl, | ||
2026 | CURLOPT_POST, | ||
2027 | 1L); | ||
2028 | curl_easy_setopt(s5r->curl, | ||
2029 | CURLOPT_WRITEFUNCTION, | ||
2030 | &curl_download_cb); | ||
2031 | curl_easy_setopt(s5r->curl, | ||
2032 | CURLOPT_WRITEDATA, | ||
2033 | s5r); | ||
2034 | curl_easy_setopt(s5r->curl, | ||
2035 | CURLOPT_READFUNCTION, | ||
2036 | &curl_upload_cb); | ||
2037 | curl_easy_setopt(s5r->curl, | ||
2038 | CURLOPT_READDATA, | ||
2039 | s5r); | ||
2040 | { | ||
2041 | const char *us; | ||
2042 | long upload_size; | ||
2043 | |||
2044 | upload_size = 0; | ||
2045 | us = MHD_lookup_connection_value(con, | ||
2046 | MHD_HEADER_KIND, | ||
2047 | MHD_HTTP_HEADER_CONTENT_LENGTH); | ||
2048 | if ((NULL != us) && | ||
2049 | (1 == sscanf(us, | ||
2050 | "%ld", | ||
2051 | &upload_size)) && | ||
2052 | (upload_size >= 0)) | ||
2053 | { | ||
2054 | curl_easy_setopt(s5r->curl, | ||
2055 | CURLOPT_INFILESIZE, | ||
2056 | upload_size); | ||
2057 | } | ||
2058 | else | ||
2059 | { | ||
2060 | curl_easy_setopt(s5r->curl, | ||
2061 | CURLOPT_INFILESIZE, | ||
2062 | upload_size); | ||
2063 | } | ||
2064 | } | ||
2065 | } | ||
2066 | else if (0 == strcasecmp(meth, | ||
2067 | MHD_HTTP_METHOD_HEAD)) | ||
2068 | { | ||
2069 | s5r->state = SOCKS5_SOCKET_DOWNLOAD_STARTED; | ||
2070 | curl_easy_setopt(s5r->curl, | ||
2071 | CURLOPT_NOBODY, | ||
2072 | 1L); | ||
2073 | } | ||
2074 | else if (0 == strcasecmp(meth, | ||
2075 | MHD_HTTP_METHOD_OPTIONS)) | ||
2076 | { | ||
2077 | s5r->state = SOCKS5_SOCKET_DOWNLOAD_STARTED; | ||
2078 | curl_easy_setopt(s5r->curl, | ||
2079 | CURLOPT_CUSTOMREQUEST, | ||
2080 | "OPTIONS"); | ||
2081 | curl_easy_setopt(s5r->curl, | ||
2082 | CURLOPT_WRITEFUNCTION, | ||
2083 | &curl_download_cb); | ||
2084 | curl_easy_setopt(s5r->curl, | ||
2085 | CURLOPT_WRITEDATA, | ||
2086 | s5r); | ||
2087 | } | ||
2088 | else if (0 == strcasecmp(meth, | ||
2089 | MHD_HTTP_METHOD_GET)) | ||
2090 | { | ||
2091 | s5r->state = SOCKS5_SOCKET_DOWNLOAD_STARTED; | ||
2092 | curl_easy_setopt(s5r->curl, | ||
2093 | CURLOPT_HTTPGET, | ||
2094 | 1L); | ||
2095 | curl_easy_setopt(s5r->curl, | ||
2096 | CURLOPT_WRITEFUNCTION, | ||
2097 | &curl_download_cb); | ||
2098 | curl_easy_setopt(s5r->curl, | ||
2099 | CURLOPT_WRITEDATA, | ||
2100 | s5r); | ||
2101 | } | ||
2102 | else if (0 == strcasecmp(meth, | ||
2103 | MHD_HTTP_METHOD_DELETE)) | ||
2104 | { | 1875 | { |
2105 | s5r->state = SOCKS5_SOCKET_DOWNLOAD_STARTED; | 1876 | GNUNET_break (0); |
2106 | curl_easy_setopt(s5r->curl, | 1877 | return MHD_NO; |
2107 | CURLOPT_CUSTOMREQUEST, | ||
2108 | "DELETE"); | ||
2109 | curl_easy_setopt(s5r->curl, | ||
2110 | CURLOPT_WRITEFUNCTION, | ||
2111 | &curl_download_cb); | ||
2112 | curl_easy_setopt(s5r->curl, | ||
2113 | CURLOPT_WRITEDATA, | ||
2114 | s5r); | ||
2115 | } | 1878 | } |
2116 | else | 1879 | GNUNET_snprintf (ipaddr, |
1880 | sizeof(ipaddr), | ||
1881 | "%s", | ||
1882 | ipstring); | ||
1883 | port = ntohs (s4->sin_port); | ||
1884 | break; | ||
1885 | |||
1886 | case AF_INET6: | ||
1887 | s6 = (const struct sockaddr_in6 *) &s5r->destination_address; | ||
1888 | if (NULL == inet_ntop (AF_INET6, | ||
1889 | &s6->sin6_addr, | ||
1890 | ipstring, | ||
1891 | sizeof(ipstring))) | ||
2117 | { | 1892 | { |
2118 | GNUNET_log(GNUNET_ERROR_TYPE_WARNING, | 1893 | GNUNET_break (0); |
2119 | _("Unsupported HTTP method `%s'\n"), | ||
2120 | meth); | ||
2121 | curl_easy_cleanup(s5r->curl); | ||
2122 | s5r->curl = NULL; | ||
2123 | return MHD_NO; | 1894 | return MHD_NO; |
2124 | } | 1895 | } |
1896 | GNUNET_snprintf (ipaddr, | ||
1897 | sizeof(ipaddr), | ||
1898 | "%s", | ||
1899 | ipstring); | ||
1900 | port = ntohs (s6->sin6_port); | ||
1901 | break; | ||
2125 | 1902 | ||
2126 | if (0 == strcasecmp(ver, MHD_HTTP_VERSION_1_0)) | 1903 | default: |
1904 | GNUNET_break (0); | ||
1905 | return MHD_NO; | ||
1906 | } | ||
1907 | } | ||
1908 | else | ||
1909 | { | ||
1910 | port = s5r->port; | ||
1911 | } | ||
1912 | if (NULL == s5r->curl) | ||
1913 | s5r->curl = curl_easy_init (); | ||
1914 | if (NULL == s5r->curl) | ||
1915 | return MHD_queue_response (con, | ||
1916 | MHD_HTTP_INTERNAL_SERVER_ERROR, | ||
1917 | curl_failure_response); | ||
1918 | curl_easy_setopt (s5r->curl, | ||
1919 | CURLOPT_HEADERFUNCTION, | ||
1920 | &curl_check_hdr); | ||
1921 | curl_easy_setopt (s5r->curl, | ||
1922 | CURLOPT_HEADERDATA, | ||
1923 | s5r); | ||
1924 | curl_easy_setopt (s5r->curl, | ||
1925 | CURLOPT_FOLLOWLOCATION, | ||
1926 | 0); | ||
1927 | if (s5r->is_gns) | ||
1928 | curl_easy_setopt (s5r->curl, | ||
1929 | CURLOPT_IPRESOLVE, | ||
1930 | CURL_IPRESOLVE_V4); | ||
1931 | curl_easy_setopt (s5r->curl, | ||
1932 | CURLOPT_CONNECTTIMEOUT, | ||
1933 | 600L); | ||
1934 | curl_easy_setopt (s5r->curl, | ||
1935 | CURLOPT_TIMEOUT, | ||
1936 | 600L); | ||
1937 | curl_easy_setopt (s5r->curl, | ||
1938 | CURLOPT_NOSIGNAL, | ||
1939 | 1L); | ||
1940 | curl_easy_setopt (s5r->curl, | ||
1941 | CURLOPT_HTTP_CONTENT_DECODING, | ||
1942 | 0); | ||
1943 | curl_easy_setopt (s5r->curl, | ||
1944 | CURLOPT_NOSIGNAL, | ||
1945 | 1L); | ||
1946 | curl_easy_setopt (s5r->curl, | ||
1947 | CURLOPT_PRIVATE, | ||
1948 | s5r); | ||
1949 | curl_easy_setopt (s5r->curl, | ||
1950 | CURLOPT_VERBOSE, | ||
1951 | 0L); | ||
1952 | /** | ||
1953 | * Pre-populate cache to resolve Hostname. | ||
1954 | * This is necessary as the DNS name in the CURLOPT_URL is used | ||
1955 | * for SNI http://de.wikipedia.org/wiki/Server_Name_Indication | ||
1956 | */ | ||
1957 | if (NULL != s5r->leho) | ||
1958 | { | ||
1959 | char *curl_hosts; | ||
1960 | |||
1961 | GNUNET_asprintf (&curl_hosts, | ||
1962 | "%s:%d:%s", | ||
1963 | s5r->leho, | ||
1964 | port, | ||
1965 | ipaddr); | ||
1966 | s5r->hosts = curl_slist_append (NULL, | ||
1967 | curl_hosts); | ||
1968 | curl_easy_setopt (s5r->curl, | ||
1969 | CURLOPT_RESOLVE, | ||
1970 | s5r->hosts); | ||
1971 | GNUNET_free (curl_hosts); | ||
1972 | } | ||
1973 | if (s5r->is_gns) | ||
1974 | { | ||
1975 | GNUNET_asprintf (&curlurl, | ||
1976 | (GNUNET_YES != s5r->is_tls) // (HTTPS_PORT != s5r->port) | ||
1977 | ? "http://%s:%d%s" | ||
1978 | : "https://%s:%d%s", | ||
1979 | (NULL != s5r->leho) | ||
1980 | ? s5r->leho | ||
1981 | : ipaddr, | ||
1982 | port, | ||
1983 | s5r->url); | ||
1984 | } | ||
1985 | else | ||
1986 | { | ||
1987 | GNUNET_asprintf (&curlurl, | ||
1988 | (GNUNET_YES != s5r->is_tls) // (HTTPS_PORT != s5r->port) | ||
1989 | ? "http://%s:%d%s" | ||
1990 | : "https://%s:%d%s", | ||
1991 | s5r->domain, | ||
1992 | port, | ||
1993 | s5r->url); | ||
1994 | } | ||
1995 | curl_easy_setopt (s5r->curl, | ||
1996 | CURLOPT_URL, | ||
1997 | curlurl); | ||
1998 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
1999 | "Launching %s CURL interaction, fetching `%s'\n", | ||
2000 | (s5r->is_gns) ? "GNS" : "DNS", | ||
2001 | curlurl); | ||
2002 | GNUNET_free (curlurl); | ||
2003 | if (0 == strcasecmp (meth, | ||
2004 | MHD_HTTP_METHOD_PUT)) | ||
2005 | { | ||
2006 | s5r->state = SOCKS5_SOCKET_UPLOAD_STARTED; | ||
2007 | curl_easy_setopt (s5r->curl, | ||
2008 | CURLOPT_UPLOAD, | ||
2009 | 1L); | ||
2010 | curl_easy_setopt (s5r->curl, | ||
2011 | CURLOPT_WRITEFUNCTION, | ||
2012 | &curl_download_cb); | ||
2013 | curl_easy_setopt (s5r->curl, | ||
2014 | CURLOPT_WRITEDATA, | ||
2015 | s5r); | ||
2016 | GNUNET_assert (CURLE_OK == | ||
2017 | curl_easy_setopt (s5r->curl, | ||
2018 | CURLOPT_READFUNCTION, | ||
2019 | &curl_upload_cb)); | ||
2020 | curl_easy_setopt (s5r->curl, | ||
2021 | CURLOPT_READDATA, | ||
2022 | s5r); | ||
2023 | { | ||
2024 | const char *us; | ||
2025 | long upload_size = 0; | ||
2026 | |||
2027 | us = MHD_lookup_connection_value (con, | ||
2028 | MHD_HEADER_KIND, | ||
2029 | MHD_HTTP_HEADER_CONTENT_LENGTH); | ||
2030 | if ((1 == sscanf (us, | ||
2031 | "%ld", | ||
2032 | &upload_size)) && | ||
2033 | (upload_size >= 0)) | ||
2127 | { | 2034 | { |
2128 | curl_easy_setopt(s5r->curl, | 2035 | curl_easy_setopt (s5r->curl, |
2129 | CURLOPT_HTTP_VERSION, | 2036 | CURLOPT_INFILESIZE, |
2130 | CURL_HTTP_VERSION_1_0); | 2037 | upload_size); |
2131 | } | 2038 | } |
2132 | else if (0 == strcasecmp(ver, MHD_HTTP_VERSION_1_1)) | 2039 | } |
2040 | } | ||
2041 | else if (0 == strcasecmp (meth, MHD_HTTP_METHOD_POST)) | ||
2042 | { | ||
2043 | s5r->state = SOCKS5_SOCKET_UPLOAD_STARTED; | ||
2044 | curl_easy_setopt (s5r->curl, | ||
2045 | CURLOPT_POST, | ||
2046 | 1L); | ||
2047 | curl_easy_setopt (s5r->curl, | ||
2048 | CURLOPT_WRITEFUNCTION, | ||
2049 | &curl_download_cb); | ||
2050 | curl_easy_setopt (s5r->curl, | ||
2051 | CURLOPT_WRITEDATA, | ||
2052 | s5r); | ||
2053 | curl_easy_setopt (s5r->curl, | ||
2054 | CURLOPT_READFUNCTION, | ||
2055 | &curl_upload_cb); | ||
2056 | curl_easy_setopt (s5r->curl, | ||
2057 | CURLOPT_READDATA, | ||
2058 | s5r); | ||
2059 | { | ||
2060 | const char *us; | ||
2061 | long upload_size; | ||
2062 | |||
2063 | upload_size = 0; | ||
2064 | us = MHD_lookup_connection_value (con, | ||
2065 | MHD_HEADER_KIND, | ||
2066 | MHD_HTTP_HEADER_CONTENT_LENGTH); | ||
2067 | if ((NULL != us) && | ||
2068 | (1 == sscanf (us, | ||
2069 | "%ld", | ||
2070 | &upload_size)) && | ||
2071 | (upload_size >= 0)) | ||
2133 | { | 2072 | { |
2134 | curl_easy_setopt(s5r->curl, | 2073 | curl_easy_setopt (s5r->curl, |
2135 | CURLOPT_HTTP_VERSION, | 2074 | CURLOPT_INFILESIZE, |
2136 | CURL_HTTP_VERSION_1_1); | 2075 | upload_size); |
2137 | } | 2076 | } |
2138 | else | 2077 | else |
2139 | { | 2078 | { |
2140 | curl_easy_setopt(s5r->curl, | 2079 | curl_easy_setopt (s5r->curl, |
2141 | CURLOPT_HTTP_VERSION, | 2080 | CURLOPT_INFILESIZE, |
2142 | CURL_HTTP_VERSION_NONE); | 2081 | upload_size); |
2143 | } | 2082 | } |
2083 | } | ||
2084 | } | ||
2085 | else if (0 == strcasecmp (meth, | ||
2086 | MHD_HTTP_METHOD_HEAD)) | ||
2087 | { | ||
2088 | s5r->state = SOCKS5_SOCKET_DOWNLOAD_STARTED; | ||
2089 | curl_easy_setopt (s5r->curl, | ||
2090 | CURLOPT_NOBODY, | ||
2091 | 1L); | ||
2092 | } | ||
2093 | else if (0 == strcasecmp (meth, | ||
2094 | MHD_HTTP_METHOD_OPTIONS)) | ||
2095 | { | ||
2096 | s5r->state = SOCKS5_SOCKET_DOWNLOAD_STARTED; | ||
2097 | curl_easy_setopt (s5r->curl, | ||
2098 | CURLOPT_CUSTOMREQUEST, | ||
2099 | "OPTIONS"); | ||
2100 | curl_easy_setopt (s5r->curl, | ||
2101 | CURLOPT_WRITEFUNCTION, | ||
2102 | &curl_download_cb); | ||
2103 | curl_easy_setopt (s5r->curl, | ||
2104 | CURLOPT_WRITEDATA, | ||
2105 | s5r); | ||
2106 | } | ||
2107 | else if (0 == strcasecmp (meth, | ||
2108 | MHD_HTTP_METHOD_GET)) | ||
2109 | { | ||
2110 | s5r->state = SOCKS5_SOCKET_DOWNLOAD_STARTED; | ||
2111 | curl_easy_setopt (s5r->curl, | ||
2112 | CURLOPT_HTTPGET, | ||
2113 | 1L); | ||
2114 | curl_easy_setopt (s5r->curl, | ||
2115 | CURLOPT_WRITEFUNCTION, | ||
2116 | &curl_download_cb); | ||
2117 | curl_easy_setopt (s5r->curl, | ||
2118 | CURLOPT_WRITEDATA, | ||
2119 | s5r); | ||
2120 | } | ||
2121 | else if (0 == strcasecmp (meth, | ||
2122 | MHD_HTTP_METHOD_DELETE)) | ||
2123 | { | ||
2124 | s5r->state = SOCKS5_SOCKET_DOWNLOAD_STARTED; | ||
2125 | curl_easy_setopt (s5r->curl, | ||
2126 | CURLOPT_CUSTOMREQUEST, | ||
2127 | "DELETE"); | ||
2128 | curl_easy_setopt (s5r->curl, | ||
2129 | CURLOPT_WRITEFUNCTION, | ||
2130 | &curl_download_cb); | ||
2131 | curl_easy_setopt (s5r->curl, | ||
2132 | CURLOPT_WRITEDATA, | ||
2133 | s5r); | ||
2134 | } | ||
2135 | else | ||
2136 | { | ||
2137 | GNUNET_log (GNUNET_ERROR_TYPE_WARNING, | ||
2138 | _ ("Unsupported HTTP method `%s'\n"), | ||
2139 | meth); | ||
2140 | curl_easy_cleanup (s5r->curl); | ||
2141 | s5r->curl = NULL; | ||
2142 | return MHD_NO; | ||
2143 | } | ||
2144 | 2144 | ||
2145 | if (GNUNET_YES == s5r->is_tls) //(HTTPS_PORT == s5r->port) | 2145 | if (0 == strcasecmp (ver, MHD_HTTP_VERSION_1_0)) |
2146 | { | 2146 | { |
2147 | curl_easy_setopt(s5r->curl, | 2147 | curl_easy_setopt (s5r->curl, |
2148 | CURLOPT_USE_SSL, | 2148 | CURLOPT_HTTP_VERSION, |
2149 | CURLUSESSL_ALL); | 2149 | CURL_HTTP_VERSION_1_0); |
2150 | if (0 < s5r->num_danes) | 2150 | } |
2151 | curl_easy_setopt(s5r->curl, | 2151 | else if (0 == strcasecmp (ver, MHD_HTTP_VERSION_1_1)) |
2152 | CURLOPT_SSL_VERIFYPEER, | 2152 | { |
2153 | 0L); | 2153 | curl_easy_setopt (s5r->curl, |
2154 | else | 2154 | CURLOPT_HTTP_VERSION, |
2155 | curl_easy_setopt(s5r->curl, | 2155 | CURL_HTTP_VERSION_1_1); |
2156 | CURLOPT_SSL_VERIFYPEER, | 2156 | } |
2157 | 1L); | 2157 | else |
2158 | /* Disable cURL checking the hostname, as we will check ourselves | 2158 | { |
2159 | as only we have the domain name or the LEHO or the DANE record */ | 2159 | curl_easy_setopt (s5r->curl, |
2160 | curl_easy_setopt(s5r->curl, | 2160 | CURLOPT_HTTP_VERSION, |
2161 | CURLOPT_SSL_VERIFYHOST, | 2161 | CURL_HTTP_VERSION_NONE); |
2162 | 0L); | 2162 | } |
2163 | } | 2163 | |
2164 | if (GNUNET_YES == s5r->is_tls) // (HTTPS_PORT == s5r->port) | ||
2165 | { | ||
2166 | curl_easy_setopt (s5r->curl, | ||
2167 | CURLOPT_USE_SSL, | ||
2168 | CURLUSESSL_ALL); | ||
2169 | if (0 < s5r->num_danes) | ||
2170 | curl_easy_setopt (s5r->curl, | ||
2171 | CURLOPT_SSL_VERIFYPEER, | ||
2172 | 0L); | ||
2164 | else | 2173 | else |
2165 | { | 2174 | curl_easy_setopt (s5r->curl, |
2166 | curl_easy_setopt(s5r->curl, | 2175 | CURLOPT_SSL_VERIFYPEER, |
2167 | CURLOPT_USE_SSL, | 2176 | 1L); |
2168 | CURLUSESSL_NONE); | 2177 | /* Disable cURL checking the hostname, as we will check ourselves |
2169 | } | 2178 | as only we have the domain name or the LEHO or the DANE record */ |
2179 | curl_easy_setopt (s5r->curl, | ||
2180 | CURLOPT_SSL_VERIFYHOST, | ||
2181 | 0L); | ||
2182 | } | ||
2183 | else | ||
2184 | { | ||
2185 | curl_easy_setopt (s5r->curl, | ||
2186 | CURLOPT_USE_SSL, | ||
2187 | CURLUSESSL_NONE); | ||
2188 | } | ||
2170 | 2189 | ||
2171 | if (CURLM_OK != | 2190 | if (CURLM_OK != |
2172 | curl_multi_add_handle(curl_multi, | 2191 | curl_multi_add_handle (curl_multi, |
2173 | s5r->curl)) | 2192 | s5r->curl)) |
2174 | { | 2193 | { |
2175 | GNUNET_break(0); | 2194 | GNUNET_break (0); |
2176 | curl_easy_cleanup(s5r->curl); | 2195 | curl_easy_cleanup (s5r->curl); |
2177 | s5r->curl = NULL; | 2196 | s5r->curl = NULL; |
2178 | return MHD_NO; | 2197 | return MHD_NO; |
2179 | } | ||
2180 | MHD_get_connection_values(con, | ||
2181 | MHD_HEADER_KIND, | ||
2182 | (MHD_KeyValueIterator) & con_val_iter, | ||
2183 | s5r); | ||
2184 | curl_easy_setopt(s5r->curl, | ||
2185 | CURLOPT_HTTPHEADER, | ||
2186 | s5r->headers); | ||
2187 | curl_download_prepare(); | ||
2188 | return MHD_YES; | ||
2189 | } | 2198 | } |
2199 | MHD_get_connection_values (con, | ||
2200 | MHD_HEADER_KIND, | ||
2201 | (MHD_KeyValueIterator) & con_val_iter, | ||
2202 | s5r); | ||
2203 | curl_easy_setopt (s5r->curl, | ||
2204 | CURLOPT_HTTPHEADER, | ||
2205 | s5r->headers); | ||
2206 | curl_download_prepare (); | ||
2207 | return MHD_YES; | ||
2208 | } | ||
2190 | 2209 | ||
2191 | /* continuing to process request */ | 2210 | /* continuing to process request */ |
2192 | if (0 != *upload_data_size) | 2211 | if (0 != *upload_data_size) |
2212 | { | ||
2213 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
2214 | "Processing %u bytes UPLOAD\n", | ||
2215 | (unsigned int) *upload_data_size); | ||
2216 | |||
2217 | /* FIXME: This must be set or a header with Transfer-Encoding: chunked. Else | ||
2218 | * upload callback is not called! | ||
2219 | */ | ||
2220 | curl_easy_setopt (s5r->curl, | ||
2221 | CURLOPT_POSTFIELDSIZE, | ||
2222 | *upload_data_size); | ||
2223 | |||
2224 | left = GNUNET_MIN (*upload_data_size, | ||
2225 | sizeof(s5r->io_buf) - s5r->io_len); | ||
2226 | GNUNET_memcpy (&s5r->io_buf[s5r->io_len], | ||
2227 | upload_data, | ||
2228 | left); | ||
2229 | s5r->io_len += left; | ||
2230 | *upload_data_size -= left; | ||
2231 | GNUNET_assert (NULL != s5r->curl); | ||
2232 | if (GNUNET_YES == s5r->curl_paused) | ||
2193 | { | 2233 | { |
2194 | GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, | 2234 | s5r->curl_paused = GNUNET_NO; |
2195 | "Processing %u bytes UPLOAD\n", | 2235 | curl_easy_pause (s5r->curl, |
2196 | (unsigned int)*upload_data_size); | 2236 | CURLPAUSE_CONT); |
2197 | |||
2198 | /* FIXME: This must be set or a header with Transfer-Encoding: chunked. Else | ||
2199 | * upload callback is not called! | ||
2200 | */ | ||
2201 | curl_easy_setopt(s5r->curl, | ||
2202 | CURLOPT_POSTFIELDSIZE, | ||
2203 | *upload_data_size); | ||
2204 | |||
2205 | left = GNUNET_MIN(*upload_data_size, | ||
2206 | sizeof(s5r->io_buf) - s5r->io_len); | ||
2207 | GNUNET_memcpy(&s5r->io_buf[s5r->io_len], | ||
2208 | upload_data, | ||
2209 | left); | ||
2210 | s5r->io_len += left; | ||
2211 | *upload_data_size -= left; | ||
2212 | GNUNET_assert(NULL != s5r->curl); | ||
2213 | if (GNUNET_YES == s5r->curl_paused) | ||
2214 | { | ||
2215 | s5r->curl_paused = GNUNET_NO; | ||
2216 | curl_easy_pause(s5r->curl, | ||
2217 | CURLPAUSE_CONT); | ||
2218 | } | ||
2219 | return MHD_YES; | ||
2220 | } | 2237 | } |
2238 | return MHD_YES; | ||
2239 | } | ||
2221 | if (SOCKS5_SOCKET_UPLOAD_STARTED == s5r->state) | 2240 | if (SOCKS5_SOCKET_UPLOAD_STARTED == s5r->state) |
2222 | { | 2241 | { |
2223 | GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, | 2242 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
2224 | "Finished processing UPLOAD\n"); | 2243 | "Finished processing UPLOAD\n"); |
2225 | s5r->state = SOCKS5_SOCKET_UPLOAD_DONE; | 2244 | s5r->state = SOCKS5_SOCKET_UPLOAD_DONE; |
2226 | } | 2245 | } |
2227 | if (NULL == s5r->response) | 2246 | if (NULL == s5r->response) |
2228 | { | 2247 | { |
2229 | GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, | 2248 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
2230 | "Waiting for HTTP response for %s%s...\n", | 2249 | "Waiting for HTTP response for %s%s...\n", |
2231 | s5r->domain, | 2250 | s5r->domain, |
2232 | s5r->url); | 2251 | s5r->url); |
2233 | MHD_suspend_connection(con); | 2252 | MHD_suspend_connection (con); |
2234 | s5r->suspended = GNUNET_YES; | 2253 | s5r->suspended = GNUNET_YES; |
2235 | return MHD_YES; | 2254 | return MHD_YES; |
2236 | } | 2255 | } |
2237 | GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, | 2256 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
2238 | "Queueing response for %s%s with MHD\n", | 2257 | "Queueing response for %s%s with MHD\n", |
2239 | s5r->domain, | 2258 | s5r->domain, |
2240 | s5r->url); | 2259 | s5r->url); |
2241 | run_mhd_now(s5r->hd); | 2260 | run_mhd_now (s5r->hd); |
2242 | return MHD_queue_response(con, | 2261 | return MHD_queue_response (con, |
2243 | s5r->response_code, | 2262 | s5r->response_code, |
2244 | s5r->response); | 2263 | s5r->response); |
2245 | } | 2264 | } |
2246 | 2265 | ||
2247 | 2266 | ||
@@ -2258,51 +2277,51 @@ create_response(void *cls, | |||
2258 | * @param toe reason for request termination (ignored) | 2277 | * @param toe reason for request termination (ignored) |
2259 | */ | 2278 | */ |
2260 | static void | 2279 | static void |
2261 | mhd_completed_cb(void *cls, | 2280 | mhd_completed_cb (void *cls, |
2262 | struct MHD_Connection *connection, | 2281 | struct MHD_Connection *connection, |
2263 | void **con_cls, | 2282 | void **con_cls, |
2264 | enum MHD_RequestTerminationCode toe) | 2283 | enum MHD_RequestTerminationCode toe) |
2265 | { | 2284 | { |
2266 | struct Socks5Request *s5r = *con_cls; | 2285 | struct Socks5Request *s5r = *con_cls; |
2267 | 2286 | ||
2268 | if (NULL == s5r) | 2287 | if (NULL == s5r) |
2269 | return; | 2288 | return; |
2270 | if (MHD_REQUEST_TERMINATED_COMPLETED_OK != toe) | 2289 | if (MHD_REQUEST_TERMINATED_COMPLETED_OK != toe) |
2271 | GNUNET_log(GNUNET_ERROR_TYPE_INFO, | 2290 | GNUNET_log (GNUNET_ERROR_TYPE_INFO, |
2272 | "MHD encountered error handling request: %d\n", | 2291 | "MHD encountered error handling request: %d\n", |
2273 | toe); | 2292 | toe); |
2274 | if (NULL != s5r->curl) | 2293 | if (NULL != s5r->curl) |
2275 | { | 2294 | { |
2276 | GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, | 2295 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
2277 | "Removing cURL handle (MHD interaction complete)\n"); | 2296 | "Removing cURL handle (MHD interaction complete)\n"); |
2278 | curl_multi_remove_handle(curl_multi, | 2297 | curl_multi_remove_handle (curl_multi, |
2279 | s5r->curl); | 2298 | s5r->curl); |
2280 | curl_slist_free_all(s5r->headers); | 2299 | curl_slist_free_all (s5r->headers); |
2281 | s5r->headers = NULL; | 2300 | s5r->headers = NULL; |
2282 | curl_easy_reset(s5r->curl); | 2301 | curl_easy_reset (s5r->curl); |
2283 | s5r->rbuf_len = 0; | 2302 | s5r->rbuf_len = 0; |
2284 | s5r->wbuf_len = 0; | 2303 | s5r->wbuf_len = 0; |
2285 | s5r->io_len = 0; | 2304 | s5r->io_len = 0; |
2286 | curl_download_prepare(); | 2305 | curl_download_prepare (); |
2287 | } | 2306 | } |
2288 | if ((NULL != s5r->response) && | 2307 | if ((NULL != s5r->response) && |
2289 | (curl_failure_response != s5r->response)) | 2308 | (curl_failure_response != s5r->response)) |
2290 | MHD_destroy_response(s5r->response); | 2309 | MHD_destroy_response (s5r->response); |
2291 | for (struct HttpResponseHeader *header = s5r->header_head; | 2310 | for (struct HttpResponseHeader *header = s5r->header_head; |
2292 | NULL != header; | 2311 | NULL != header; |
2293 | header = s5r->header_head) | 2312 | header = s5r->header_head) |
2294 | { | 2313 | { |
2295 | GNUNET_CONTAINER_DLL_remove(s5r->header_head, | 2314 | GNUNET_CONTAINER_DLL_remove (s5r->header_head, |
2296 | s5r->header_tail, | 2315 | s5r->header_tail, |
2297 | header); | 2316 | header); |
2298 | GNUNET_free(header->type); | 2317 | GNUNET_free (header->type); |
2299 | GNUNET_free(header->value); | 2318 | GNUNET_free (header->value); |
2300 | GNUNET_free(header); | 2319 | GNUNET_free (header); |
2301 | } | 2320 | } |
2302 | GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, | 2321 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
2303 | "Finished request for %s\n", | 2322 | "Finished request for %s\n", |
2304 | s5r->url); | 2323 | s5r->url); |
2305 | GNUNET_free(s5r->url); | 2324 | GNUNET_free (s5r->url); |
2306 | s5r->state = SOCKS5_SOCKET_WITH_MHD; | 2325 | s5r->state = SOCKS5_SOCKET_WITH_MHD; |
2307 | s5r->url = NULL; | 2326 | s5r->url = NULL; |
2308 | s5r->response = NULL; | 2327 | s5r->response = NULL; |
@@ -2320,58 +2339,58 @@ mhd_completed_cb(void *cls, | |||
2320 | * @param toe connection notification type | 2339 | * @param toe connection notification type |
2321 | */ | 2340 | */ |
2322 | static void | 2341 | static void |
2323 | mhd_connection_cb(void *cls, | 2342 | mhd_connection_cb (void *cls, |
2324 | struct MHD_Connection *connection, | 2343 | struct MHD_Connection *connection, |
2325 | void **con_cls, | 2344 | void **con_cls, |
2326 | enum MHD_ConnectionNotificationCode cnc) | 2345 | enum MHD_ConnectionNotificationCode cnc) |
2327 | { | 2346 | { |
2328 | struct Socks5Request *s5r; | 2347 | struct Socks5Request *s5r; |
2329 | const union MHD_ConnectionInfo *ci; | 2348 | const union MHD_ConnectionInfo *ci; |
2330 | int sock; | 2349 | int sock; |
2331 | 2350 | ||
2332 | switch (cnc) | 2351 | switch (cnc) |
2352 | { | ||
2353 | case MHD_CONNECTION_NOTIFY_STARTED: | ||
2354 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Connection started...\n"); | ||
2355 | ci = MHD_get_connection_info (connection, | ||
2356 | MHD_CONNECTION_INFO_CONNECTION_FD); | ||
2357 | if (NULL == ci) | ||
2333 | { | 2358 | { |
2334 | case MHD_CONNECTION_NOTIFY_STARTED: | 2359 | GNUNET_break (0); |
2335 | GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, "Connection started...\n"); | 2360 | return; |
2336 | ci = MHD_get_connection_info(connection, | 2361 | } |
2337 | MHD_CONNECTION_INFO_CONNECTION_FD); | 2362 | sock = ci->connect_fd; |
2338 | if (NULL == ci) | 2363 | for (s5r = s5r_head; NULL != s5r; s5r = s5r->next) |
2339 | { | 2364 | { |
2340 | GNUNET_break(0); | 2365 | if (GNUNET_NETWORK_get_fd (s5r->sock) == sock) |
2341 | return; | 2366 | { |
2342 | } | 2367 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
2343 | sock = ci->connect_fd; | 2368 | "Context set...\n"); |
2344 | for (s5r = s5r_head; NULL != s5r; s5r = s5r->next) | 2369 | s5r->ssl_checked = GNUNET_NO; |
2345 | { | 2370 | *con_cls = s5r; |
2346 | if (GNUNET_NETWORK_get_fd(s5r->sock) == sock) | 2371 | break; |
2347 | { | 2372 | } |
2348 | GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, | 2373 | } |
2349 | "Context set...\n"); | 2374 | break; |
2350 | s5r->ssl_checked = GNUNET_NO; | ||
2351 | *con_cls = s5r; | ||
2352 | break; | ||
2353 | } | ||
2354 | } | ||
2355 | break; | ||
2356 | |||
2357 | case MHD_CONNECTION_NOTIFY_CLOSED: | ||
2358 | GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, | ||
2359 | "Connection closed... cleaning up\n"); | ||
2360 | s5r = *con_cls; | ||
2361 | if (NULL == s5r) | ||
2362 | { | ||
2363 | GNUNET_log(GNUNET_ERROR_TYPE_ERROR, | ||
2364 | "Connection stale!\n"); | ||
2365 | return; | ||
2366 | } | ||
2367 | cleanup_s5r(s5r); | ||
2368 | curl_download_prepare(); | ||
2369 | *con_cls = NULL; | ||
2370 | break; | ||
2371 | 2375 | ||
2372 | default: | 2376 | case MHD_CONNECTION_NOTIFY_CLOSED: |
2373 | GNUNET_break(0); | 2377 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
2378 | "Connection closed... cleaning up\n"); | ||
2379 | s5r = *con_cls; | ||
2380 | if (NULL == s5r) | ||
2381 | { | ||
2382 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, | ||
2383 | "Connection stale!\n"); | ||
2384 | return; | ||
2374 | } | 2385 | } |
2386 | cleanup_s5r (s5r); | ||
2387 | curl_download_prepare (); | ||
2388 | *con_cls = NULL; | ||
2389 | break; | ||
2390 | |||
2391 | default: | ||
2392 | GNUNET_break (0); | ||
2393 | } | ||
2375 | } | 2394 | } |
2376 | 2395 | ||
2377 | /** | 2396 | /** |
@@ -2388,34 +2407,34 @@ mhd_connection_cb(void *cls, | |||
2388 | * @return the `struct Socks5Request` that this @a connection is for | 2407 | * @return the `struct Socks5Request` that this @a connection is for |
2389 | */ | 2408 | */ |
2390 | static void * | 2409 | static void * |
2391 | mhd_log_callback(void *cls, | 2410 | mhd_log_callback (void *cls, |
2392 | const char *url, | 2411 | const char *url, |
2393 | struct MHD_Connection *connection) | 2412 | struct MHD_Connection *connection) |
2394 | { | 2413 | { |
2395 | struct Socks5Request *s5r; | 2414 | struct Socks5Request *s5r; |
2396 | const union MHD_ConnectionInfo *ci; | 2415 | const union MHD_ConnectionInfo *ci; |
2397 | 2416 | ||
2398 | ci = MHD_get_connection_info(connection, | 2417 | ci = MHD_get_connection_info (connection, |
2399 | MHD_CONNECTION_INFO_SOCKET_CONTEXT); | 2418 | MHD_CONNECTION_INFO_SOCKET_CONTEXT); |
2400 | GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, "Processing %s\n", url); | 2419 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Processing %s\n", url); |
2401 | if (NULL == ci) | 2420 | if (NULL == ci) |
2402 | { | 2421 | { |
2403 | GNUNET_break(0); | 2422 | GNUNET_break (0); |
2404 | return NULL; | 2423 | return NULL; |
2405 | } | 2424 | } |
2406 | s5r = ci->socket_context; | 2425 | s5r = ci->socket_context; |
2407 | if (NULL != s5r->url) | 2426 | if (NULL != s5r->url) |
2408 | { | 2427 | { |
2409 | GNUNET_break(0); | 2428 | GNUNET_break (0); |
2410 | return NULL; | 2429 | return NULL; |
2411 | } | 2430 | } |
2412 | s5r->url = GNUNET_strdup(url); | 2431 | s5r->url = GNUNET_strdup (url); |
2413 | if (NULL != s5r->timeout_task) | 2432 | if (NULL != s5r->timeout_task) |
2414 | { | 2433 | { |
2415 | GNUNET_SCHEDULER_cancel(s5r->timeout_task); | 2434 | GNUNET_SCHEDULER_cancel (s5r->timeout_task); |
2416 | s5r->timeout_task = NULL; | 2435 | s5r->timeout_task = NULL; |
2417 | } | 2436 | } |
2418 | GNUNET_assert(s5r->state == SOCKS5_SOCKET_WITH_MHD); | 2437 | GNUNET_assert (s5r->state == SOCKS5_SOCKET_WITH_MHD); |
2419 | return s5r; | 2438 | return s5r; |
2420 | } | 2439 | } |
2421 | 2440 | ||
@@ -2426,22 +2445,22 @@ mhd_log_callback(void *cls, | |||
2426 | * @param hd daemon to stop | 2445 | * @param hd daemon to stop |
2427 | */ | 2446 | */ |
2428 | static void | 2447 | static void |
2429 | kill_httpd(struct MhdHttpList *hd) | 2448 | kill_httpd (struct MhdHttpList *hd) |
2430 | { | 2449 | { |
2431 | GNUNET_CONTAINER_DLL_remove(mhd_httpd_head, | 2450 | GNUNET_CONTAINER_DLL_remove (mhd_httpd_head, |
2432 | mhd_httpd_tail, | 2451 | mhd_httpd_tail, |
2433 | hd); | 2452 | hd); |
2434 | GNUNET_free_non_null(hd->domain); | 2453 | GNUNET_free_non_null (hd->domain); |
2435 | MHD_stop_daemon(hd->daemon); | 2454 | MHD_stop_daemon (hd->daemon); |
2436 | if (NULL != hd->httpd_task) | 2455 | if (NULL != hd->httpd_task) |
2437 | { | 2456 | { |
2438 | GNUNET_SCHEDULER_cancel(hd->httpd_task); | 2457 | GNUNET_SCHEDULER_cancel (hd->httpd_task); |
2439 | hd->httpd_task = NULL; | 2458 | hd->httpd_task = NULL; |
2440 | } | 2459 | } |
2441 | GNUNET_free_non_null(hd->proxy_cert); | 2460 | GNUNET_free_non_null (hd->proxy_cert); |
2442 | if (hd == httpd) | 2461 | if (hd == httpd) |
2443 | httpd = NULL; | 2462 | httpd = NULL; |
2444 | GNUNET_free(hd); | 2463 | GNUNET_free (hd); |
2445 | } | 2464 | } |
2446 | 2465 | ||
2447 | 2466 | ||
@@ -2451,12 +2470,12 @@ kill_httpd(struct MhdHttpList *hd) | |||
2451 | * @param cls the `struct MhdHttpList *` | 2470 | * @param cls the `struct MhdHttpList *` |
2452 | */ | 2471 | */ |
2453 | static void | 2472 | static void |
2454 | kill_httpd_task(void *cls) | 2473 | kill_httpd_task (void *cls) |
2455 | { | 2474 | { |
2456 | struct MhdHttpList *hd = cls; | 2475 | struct MhdHttpList *hd = cls; |
2457 | 2476 | ||
2458 | hd->httpd_task = NULL; | 2477 | hd->httpd_task = NULL; |
2459 | kill_httpd(hd); | 2478 | kill_httpd (hd); |
2460 | } | 2479 | } |
2461 | 2480 | ||
2462 | 2481 | ||
@@ -2466,7 +2485,7 @@ kill_httpd_task(void *cls) | |||
2466 | * @param cls the `struct MhdHttpList *` of the daemon that is being run | 2485 | * @param cls the `struct MhdHttpList *` of the daemon that is being run |
2467 | */ | 2486 | */ |
2468 | static void | 2487 | static void |
2469 | do_httpd(void *cls); | 2488 | do_httpd (void *cls); |
2470 | 2489 | ||
2471 | 2490 | ||
2472 | /** | 2491 | /** |
@@ -2477,7 +2496,7 @@ do_httpd(void *cls); | |||
2477 | * @param hd the daemon to schedule | 2496 | * @param hd the daemon to schedule |
2478 | */ | 2497 | */ |
2479 | static void | 2498 | static void |
2480 | schedule_httpd(struct MhdHttpList *hd) | 2499 | schedule_httpd (struct MhdHttpList *hd) |
2481 | { | 2500 | { |
2482 | fd_set rs; | 2501 | fd_set rs; |
2483 | fd_set ws; | 2502 | fd_set ws; |
@@ -2489,63 +2508,63 @@ schedule_httpd(struct MhdHttpList *hd) | |||
2489 | MHD_UNSIGNED_LONG_LONG timeout; | 2508 | MHD_UNSIGNED_LONG_LONG timeout; |
2490 | struct GNUNET_TIME_Relative tv; | 2509 | struct GNUNET_TIME_Relative tv; |
2491 | 2510 | ||
2492 | FD_ZERO(&rs); | 2511 | FD_ZERO (&rs); |
2493 | FD_ZERO(&ws); | 2512 | FD_ZERO (&ws); |
2494 | FD_ZERO(&es); | 2513 | FD_ZERO (&es); |
2495 | max = -1; | 2514 | max = -1; |
2496 | if (MHD_YES != | 2515 | if (MHD_YES != |
2497 | MHD_get_fdset(hd->daemon, | 2516 | MHD_get_fdset (hd->daemon, |
2498 | &rs, | 2517 | &rs, |
2499 | &ws, | 2518 | &ws, |
2500 | &es, | 2519 | &es, |
2501 | &max)) | 2520 | &max)) |
2502 | { | 2521 | { |
2503 | kill_httpd(hd); | 2522 | kill_httpd (hd); |
2504 | return; | 2523 | return; |
2505 | } | 2524 | } |
2506 | haveto = MHD_get_timeout(hd->daemon, | 2525 | haveto = MHD_get_timeout (hd->daemon, |
2507 | &timeout); | 2526 | &timeout); |
2508 | if (MHD_YES == haveto) | 2527 | if (MHD_YES == haveto) |
2509 | tv.rel_value_us = (uint64_t)timeout * 1000LL; | 2528 | tv.rel_value_us = (uint64_t) timeout * 1000LL; |
2510 | else | 2529 | else |
2511 | tv = GNUNET_TIME_UNIT_FOREVER_REL; | 2530 | tv = GNUNET_TIME_UNIT_FOREVER_REL; |
2512 | if (-1 != max) | 2531 | if (-1 != max) |
2513 | { | 2532 | { |
2514 | wrs = GNUNET_NETWORK_fdset_create(); | 2533 | wrs = GNUNET_NETWORK_fdset_create (); |
2515 | wws = GNUNET_NETWORK_fdset_create(); | 2534 | wws = GNUNET_NETWORK_fdset_create (); |
2516 | GNUNET_NETWORK_fdset_copy_native(wrs, &rs, max + 1); | 2535 | GNUNET_NETWORK_fdset_copy_native (wrs, &rs, max + 1); |
2517 | GNUNET_NETWORK_fdset_copy_native(wws, &ws, max + 1); | 2536 | GNUNET_NETWORK_fdset_copy_native (wws, &ws, max + 1); |
2518 | } | 2537 | } |
2519 | else | 2538 | else |
2520 | { | 2539 | { |
2521 | wrs = NULL; | 2540 | wrs = NULL; |
2522 | wws = NULL; | 2541 | wws = NULL; |
2523 | } | 2542 | } |
2524 | if (NULL != hd->httpd_task) | 2543 | if (NULL != hd->httpd_task) |
2525 | { | 2544 | { |
2526 | GNUNET_SCHEDULER_cancel(hd->httpd_task); | 2545 | GNUNET_SCHEDULER_cancel (hd->httpd_task); |
2527 | hd->httpd_task = NULL; | 2546 | hd->httpd_task = NULL; |
2528 | } | 2547 | } |
2529 | if ((MHD_YES != haveto) && | 2548 | if ((MHD_YES != haveto) && |
2530 | (-1 == max) && | 2549 | (-1 == max) && |
2531 | (hd != httpd)) | 2550 | (hd != httpd)) |
2532 | { | 2551 | { |
2533 | /* daemon is idle, kill after timeout */ | 2552 | /* daemon is idle, kill after timeout */ |
2534 | hd->httpd_task = GNUNET_SCHEDULER_add_delayed(MHD_CACHE_TIMEOUT, | 2553 | hd->httpd_task = GNUNET_SCHEDULER_add_delayed (MHD_CACHE_TIMEOUT, |
2535 | &kill_httpd_task, | 2554 | &kill_httpd_task, |
2536 | hd); | 2555 | hd); |
2537 | } | 2556 | } |
2538 | else | 2557 | else |
2539 | { | 2558 | { |
2540 | hd->httpd_task = | 2559 | hd->httpd_task = |
2541 | GNUNET_SCHEDULER_add_select(GNUNET_SCHEDULER_PRIORITY_DEFAULT, | 2560 | GNUNET_SCHEDULER_add_select (GNUNET_SCHEDULER_PRIORITY_DEFAULT, |
2542 | tv, wrs, wws, | 2561 | tv, wrs, wws, |
2543 | &do_httpd, hd); | 2562 | &do_httpd, hd); |
2544 | } | 2563 | } |
2545 | if (NULL != wrs) | 2564 | if (NULL != wrs) |
2546 | GNUNET_NETWORK_fdset_destroy(wrs); | 2565 | GNUNET_NETWORK_fdset_destroy (wrs); |
2547 | if (NULL != wws) | 2566 | if (NULL != wws) |
2548 | GNUNET_NETWORK_fdset_destroy(wws); | 2567 | GNUNET_NETWORK_fdset_destroy (wws); |
2549 | } | 2568 | } |
2550 | 2569 | ||
2551 | 2570 | ||
@@ -2555,13 +2574,13 @@ schedule_httpd(struct MhdHttpList *hd) | |||
2555 | * @param cls the `struct MhdHttpList` of the daemon that is being run | 2574 | * @param cls the `struct MhdHttpList` of the daemon that is being run |
2556 | */ | 2575 | */ |
2557 | static void | 2576 | static void |
2558 | do_httpd(void *cls) | 2577 | do_httpd (void *cls) |
2559 | { | 2578 | { |
2560 | struct MhdHttpList *hd = cls; | 2579 | struct MhdHttpList *hd = cls; |
2561 | 2580 | ||
2562 | hd->httpd_task = NULL; | 2581 | hd->httpd_task = NULL; |
2563 | MHD_run(hd->daemon); | 2582 | MHD_run (hd->daemon); |
2564 | schedule_httpd(hd); | 2583 | schedule_httpd (hd); |
2565 | } | 2584 | } |
2566 | 2585 | ||
2567 | 2586 | ||
@@ -2571,12 +2590,12 @@ do_httpd(void *cls) | |||
2571 | * @param hd the daemon to run now. | 2590 | * @param hd the daemon to run now. |
2572 | */ | 2591 | */ |
2573 | static void | 2592 | static void |
2574 | run_mhd_now(struct MhdHttpList *hd) | 2593 | run_mhd_now (struct MhdHttpList *hd) |
2575 | { | 2594 | { |
2576 | if (NULL != hd->httpd_task) | 2595 | if (NULL != hd->httpd_task) |
2577 | GNUNET_SCHEDULER_cancel(hd->httpd_task); | 2596 | GNUNET_SCHEDULER_cancel (hd->httpd_task); |
2578 | hd->httpd_task = GNUNET_SCHEDULER_add_now(&do_httpd, | 2597 | hd->httpd_task = GNUNET_SCHEDULER_add_now (&do_httpd, |
2579 | hd); | 2598 | hd); |
2580 | } | 2599 | } |
2581 | 2600 | ||
2582 | 2601 | ||
@@ -2588,30 +2607,30 @@ run_mhd_now(struct MhdHttpList *hd) | |||
2588 | * @return NULL on error | 2607 | * @return NULL on error |
2589 | */ | 2608 | */ |
2590 | static void* | 2609 | static void* |
2591 | load_file(const char* filename, | 2610 | load_file (const char*filename, |
2592 | unsigned int* size) | 2611 | unsigned int*size) |
2593 | { | 2612 | { |
2594 | void *buffer; | 2613 | void *buffer; |
2595 | uint64_t fsize; | 2614 | uint64_t fsize; |
2596 | 2615 | ||
2597 | if (GNUNET_OK != | 2616 | if (GNUNET_OK != |
2598 | GNUNET_DISK_file_size(filename, | 2617 | GNUNET_DISK_file_size (filename, |
2599 | &fsize, | 2618 | &fsize, |
2600 | GNUNET_YES, | 2619 | GNUNET_YES, |
2601 | GNUNET_YES)) | 2620 | GNUNET_YES)) |
2602 | return NULL; | 2621 | return NULL; |
2603 | if (fsize > MAX_PEM_SIZE) | 2622 | if (fsize > MAX_PEM_SIZE) |
2604 | return NULL; | 2623 | return NULL; |
2605 | *size = (unsigned int)fsize; | 2624 | *size = (unsigned int) fsize; |
2606 | buffer = GNUNET_malloc(*size); | 2625 | buffer = GNUNET_malloc (*size); |
2607 | if (fsize != | 2626 | if (fsize != |
2608 | GNUNET_DISK_fn_read(filename, | 2627 | GNUNET_DISK_fn_read (filename, |
2609 | buffer, | 2628 | buffer, |
2610 | (size_t)fsize)) | 2629 | (size_t) fsize)) |
2611 | { | 2630 | { |
2612 | GNUNET_free(buffer); | 2631 | GNUNET_free (buffer); |
2613 | return NULL; | 2632 | return NULL; |
2614 | } | 2633 | } |
2615 | return buffer; | 2634 | return buffer; |
2616 | } | 2635 | } |
2617 | 2636 | ||
@@ -2624,25 +2643,25 @@ load_file(const char* filename, | |||
2624 | * @return #GNUNET_OK on success | 2643 | * @return #GNUNET_OK on success |
2625 | */ | 2644 | */ |
2626 | static int | 2645 | static int |
2627 | load_key_from_file(gnutls_x509_privkey_t key, | 2646 | load_key_from_file (gnutls_x509_privkey_t key, |
2628 | const char* keyfile) | 2647 | const char*keyfile) |
2629 | { | 2648 | { |
2630 | gnutls_datum_t key_data; | 2649 | gnutls_datum_t key_data; |
2631 | int ret; | 2650 | int ret; |
2632 | 2651 | ||
2633 | key_data.data = load_file(keyfile, | 2652 | key_data.data = load_file (keyfile, |
2634 | &key_data.size); | 2653 | &key_data.size); |
2635 | if (NULL == key_data.data) | 2654 | if (NULL == key_data.data) |
2636 | return GNUNET_SYSERR; | 2655 | return GNUNET_SYSERR; |
2637 | ret = gnutls_x509_privkey_import(key, &key_data, | 2656 | ret = gnutls_x509_privkey_import (key, &key_data, |
2638 | GNUTLS_X509_FMT_PEM); | 2657 | GNUTLS_X509_FMT_PEM); |
2639 | if (GNUTLS_E_SUCCESS != ret) | 2658 | if (GNUTLS_E_SUCCESS != ret) |
2640 | { | 2659 | { |
2641 | GNUNET_log(GNUNET_ERROR_TYPE_ERROR, | 2660 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, |
2642 | _("Unable to import private key from file `%s'\n"), | 2661 | _ ("Unable to import private key from file `%s'\n"), |
2643 | keyfile); | 2662 | keyfile); |
2644 | } | 2663 | } |
2645 | GNUNET_free_non_null(key_data.data); | 2664 | GNUNET_free_non_null (key_data.data); |
2646 | return (GNUTLS_E_SUCCESS != ret) ? GNUNET_SYSERR : GNUNET_OK; | 2665 | return (GNUTLS_E_SUCCESS != ret) ? GNUNET_SYSERR : GNUNET_OK; |
2647 | } | 2666 | } |
2648 | 2667 | ||
@@ -2655,26 +2674,26 @@ load_key_from_file(gnutls_x509_privkey_t key, | |||
2655 | * @return #GNUNET_OK on success | 2674 | * @return #GNUNET_OK on success |
2656 | */ | 2675 | */ |
2657 | static int | 2676 | static int |
2658 | load_cert_from_file(gnutls_x509_crt_t crt, | 2677 | load_cert_from_file (gnutls_x509_crt_t crt, |
2659 | const char* certfile) | 2678 | const char*certfile) |
2660 | { | 2679 | { |
2661 | gnutls_datum_t cert_data; | 2680 | gnutls_datum_t cert_data; |
2662 | int ret; | 2681 | int ret; |
2663 | 2682 | ||
2664 | cert_data.data = load_file(certfile, | 2683 | cert_data.data = load_file (certfile, |
2665 | &cert_data.size); | 2684 | &cert_data.size); |
2666 | if (NULL == cert_data.data) | 2685 | if (NULL == cert_data.data) |
2667 | return GNUNET_SYSERR; | 2686 | return GNUNET_SYSERR; |
2668 | ret = gnutls_x509_crt_import(crt, | 2687 | ret = gnutls_x509_crt_import (crt, |
2669 | &cert_data, | 2688 | &cert_data, |
2670 | GNUTLS_X509_FMT_PEM); | 2689 | GNUTLS_X509_FMT_PEM); |
2671 | if (GNUTLS_E_SUCCESS != ret) | 2690 | if (GNUTLS_E_SUCCESS != ret) |
2672 | { | 2691 | { |
2673 | GNUNET_log(GNUNET_ERROR_TYPE_ERROR, | 2692 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, |
2674 | _("Unable to import certificate from `%s'\n"), | 2693 | _ ("Unable to import certificate from `%s'\n"), |
2675 | certfile); | 2694 | certfile); |
2676 | } | 2695 | } |
2677 | GNUNET_free_non_null(cert_data.data); | 2696 | GNUNET_free_non_null (cert_data.data); |
2678 | return (GNUTLS_E_SUCCESS != ret) ? GNUNET_SYSERR : GNUNET_OK; | 2697 | return (GNUTLS_E_SUCCESS != ret) ? GNUNET_SYSERR : GNUNET_OK; |
2679 | } | 2698 | } |
2680 | 2699 | ||
@@ -2686,7 +2705,7 @@ load_cert_from_file(gnutls_x509_crt_t crt, | |||
2686 | * @return a struct holding the PEM data, NULL on error | 2705 | * @return a struct holding the PEM data, NULL on error |
2687 | */ | 2706 | */ |
2688 | static struct ProxyGNSCertificate * | 2707 | static struct ProxyGNSCertificate * |
2689 | generate_gns_certificate(const char *name) | 2708 | generate_gns_certificate (const char *name) |
2690 | { | 2709 | { |
2691 | unsigned int serial; | 2710 | unsigned int serial; |
2692 | size_t key_buf_size; | 2711 | size_t key_buf_size; |
@@ -2696,65 +2715,66 @@ generate_gns_certificate(const char *name) | |||
2696 | struct tm *tm_data; | 2715 | struct tm *tm_data; |
2697 | struct ProxyGNSCertificate *pgc; | 2716 | struct ProxyGNSCertificate *pgc; |
2698 | 2717 | ||
2699 | GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, | 2718 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
2700 | "Generating x.509 certificate for `%s'\n", | 2719 | "Generating x.509 certificate for `%s'\n", |
2701 | name); | 2720 | name); |
2702 | GNUNET_break(GNUTLS_E_SUCCESS == gnutls_x509_crt_init(&request)); | 2721 | GNUNET_break (GNUTLS_E_SUCCESS == gnutls_x509_crt_init (&request)); |
2703 | GNUNET_break(GNUTLS_E_SUCCESS == gnutls_x509_crt_set_key(request, proxy_ca.key)); | 2722 | GNUNET_break (GNUTLS_E_SUCCESS == gnutls_x509_crt_set_key (request, |
2704 | pgc = GNUNET_new(struct ProxyGNSCertificate); | 2723 | proxy_ca.key)); |
2705 | gnutls_x509_crt_set_dn_by_oid(request, | 2724 | pgc = GNUNET_new (struct ProxyGNSCertificate); |
2706 | GNUTLS_OID_X520_COUNTRY_NAME, | 2725 | gnutls_x509_crt_set_dn_by_oid (request, |
2707 | 0, | 2726 | GNUTLS_OID_X520_COUNTRY_NAME, |
2708 | "ZZ", | 2727 | 0, |
2709 | strlen("ZZ")); | 2728 | "ZZ", |
2710 | gnutls_x509_crt_set_dn_by_oid(request, | 2729 | strlen ("ZZ")); |
2711 | GNUTLS_OID_X520_ORGANIZATION_NAME, | 2730 | gnutls_x509_crt_set_dn_by_oid (request, |
2712 | 0, | 2731 | GNUTLS_OID_X520_ORGANIZATION_NAME, |
2713 | "GNU Name System", | 2732 | 0, |
2714 | strlen("GNU Name System")); | 2733 | "GNU Name System", |
2715 | gnutls_x509_crt_set_dn_by_oid(request, | 2734 | strlen ("GNU Name System")); |
2716 | GNUTLS_OID_X520_COMMON_NAME, | 2735 | gnutls_x509_crt_set_dn_by_oid (request, |
2717 | 0, | 2736 | GNUTLS_OID_X520_COMMON_NAME, |
2718 | name, | 2737 | 0, |
2719 | strlen(name)); | 2738 | name, |
2720 | gnutls_x509_crt_set_subject_alternative_name(request, | 2739 | strlen (name)); |
2721 | GNUTLS_SAN_DNSNAME, | 2740 | gnutls_x509_crt_set_subject_alternative_name (request, |
2722 | name); | 2741 | GNUTLS_SAN_DNSNAME, |
2723 | GNUNET_break(GNUTLS_E_SUCCESS == | 2742 | name); |
2724 | gnutls_x509_crt_set_version(request, | 2743 | GNUNET_break (GNUTLS_E_SUCCESS == |
2725 | 3)); | 2744 | gnutls_x509_crt_set_version (request, |
2726 | gnutls_rnd(GNUTLS_RND_NONCE, | 2745 | 3)); |
2727 | &serial, | 2746 | gnutls_rnd (GNUTLS_RND_NONCE, |
2728 | sizeof(serial)); | 2747 | &serial, |
2729 | gnutls_x509_crt_set_serial(request, | 2748 | sizeof(serial)); |
2730 | &serial, | 2749 | gnutls_x509_crt_set_serial (request, |
2731 | sizeof(serial)); | 2750 | &serial, |
2732 | etime = time(NULL); | 2751 | sizeof(serial)); |
2733 | tm_data = localtime(&etime); | 2752 | etime = time (NULL); |
2753 | tm_data = localtime (&etime); | ||
2734 | tm_data->tm_hour--; | 2754 | tm_data->tm_hour--; |
2735 | etime = mktime(tm_data); | 2755 | etime = mktime (tm_data); |
2736 | gnutls_x509_crt_set_activation_time(request, | 2756 | gnutls_x509_crt_set_activation_time (request, |
2737 | etime); | 2757 | etime); |
2738 | tm_data->tm_year++; | 2758 | tm_data->tm_year++; |
2739 | etime = mktime(tm_data); | 2759 | etime = mktime (tm_data); |
2740 | gnutls_x509_crt_set_expiration_time(request, | 2760 | gnutls_x509_crt_set_expiration_time (request, |
2741 | etime); | 2761 | etime); |
2742 | gnutls_x509_crt_sign2(request, | 2762 | gnutls_x509_crt_sign2 (request, |
2743 | proxy_ca.cert, | 2763 | proxy_ca.cert, |
2744 | proxy_ca.key, | 2764 | proxy_ca.key, |
2745 | GNUTLS_DIG_SHA512, | 2765 | GNUTLS_DIG_SHA512, |
2746 | 0); | 2766 | 0); |
2747 | key_buf_size = sizeof(pgc->key); | 2767 | key_buf_size = sizeof(pgc->key); |
2748 | cert_buf_size = sizeof(pgc->cert); | 2768 | cert_buf_size = sizeof(pgc->cert); |
2749 | gnutls_x509_crt_export(request, | 2769 | gnutls_x509_crt_export (request, |
2750 | GNUTLS_X509_FMT_PEM, | 2770 | GNUTLS_X509_FMT_PEM, |
2751 | pgc->cert, | 2771 | pgc->cert, |
2752 | &cert_buf_size); | 2772 | &cert_buf_size); |
2753 | gnutls_x509_privkey_export(proxy_ca.key, | 2773 | gnutls_x509_privkey_export (proxy_ca.key, |
2754 | GNUTLS_X509_FMT_PEM, | 2774 | GNUTLS_X509_FMT_PEM, |
2755 | pgc->key, | 2775 | pgc->key, |
2756 | &key_buf_size); | 2776 | &key_buf_size); |
2757 | gnutls_x509_crt_deinit(request); | 2777 | gnutls_x509_crt_deinit (request); |
2758 | return pgc; | 2778 | return pgc; |
2759 | } | 2779 | } |
2760 | 2780 | ||
@@ -2767,9 +2787,9 @@ generate_gns_certificate(const char *name) | |||
2767 | * @param ap arguments to @a fm | 2787 | * @param ap arguments to @a fm |
2768 | */ | 2788 | */ |
2769 | static void | 2789 | static void |
2770 | mhd_error_log_callback(void *cls, | 2790 | mhd_error_log_callback (void *cls, |
2771 | const char *fm, | 2791 | const char *fm, |
2772 | va_list ap) | 2792 | va_list ap) |
2773 | { | 2793 | { |
2774 | /* do nothing */ | 2794 | /* do nothing */ |
2775 | } | 2795 | } |
@@ -2782,49 +2802,56 @@ mhd_error_log_callback(void *cls, | |||
2782 | * @return NULL on error | 2802 | * @return NULL on error |
2783 | */ | 2803 | */ |
2784 | static struct MhdHttpList * | 2804 | static struct MhdHttpList * |
2785 | lookup_ssl_httpd(const char* domain) | 2805 | lookup_ssl_httpd (const char*domain) |
2786 | { | 2806 | { |
2787 | struct MhdHttpList *hd; | 2807 | struct MhdHttpList *hd; |
2788 | struct ProxyGNSCertificate *pgc; | 2808 | struct ProxyGNSCertificate *pgc; |
2789 | 2809 | ||
2790 | if (NULL == domain) | 2810 | if (NULL == domain) |
2791 | { | 2811 | { |
2792 | GNUNET_break(0); | 2812 | GNUNET_break (0); |
2793 | return NULL; | 2813 | return NULL; |
2794 | } | 2814 | } |
2795 | for (hd = mhd_httpd_head; NULL != hd; hd = hd->next) | 2815 | for (hd = mhd_httpd_head; NULL != hd; hd = hd->next) |
2796 | if ((NULL != hd->domain) && | 2816 | if ((NULL != hd->domain) && |
2797 | (0 == strcmp(hd->domain, domain))) | 2817 | (0 == strcmp (hd->domain, domain))) |
2798 | return hd; | 2818 | return hd; |
2799 | GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, | 2819 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
2800 | "Starting fresh MHD HTTPS instance for domain `%s'\n", | 2820 | "Starting fresh MHD HTTPS instance for domain `%s'\n", |
2801 | domain); | 2821 | domain); |
2802 | pgc = generate_gns_certificate(domain); | 2822 | pgc = generate_gns_certificate (domain); |
2803 | hd = GNUNET_new(struct MhdHttpList); | 2823 | hd = GNUNET_new (struct MhdHttpList); |
2804 | hd->is_ssl = GNUNET_YES; | 2824 | hd->is_ssl = GNUNET_YES; |
2805 | hd->domain = GNUNET_strdup(domain); | 2825 | hd->domain = GNUNET_strdup (domain); |
2806 | hd->proxy_cert = pgc; | 2826 | hd->proxy_cert = pgc; |
2807 | hd->daemon = MHD_start_daemon(MHD_USE_DEBUG | MHD_USE_SSL | MHD_USE_NO_LISTEN_SOCKET | MHD_ALLOW_SUSPEND_RESUME, | 2827 | hd->daemon = MHD_start_daemon (MHD_USE_DEBUG | MHD_USE_SSL |
2808 | 0, | 2828 | | MHD_USE_NO_LISTEN_SOCKET |
2809 | NULL, NULL, | 2829 | | MHD_ALLOW_SUSPEND_RESUME, |
2810 | &create_response, hd, | 2830 | 0, |
2811 | MHD_OPTION_CONNECTION_TIMEOUT, (unsigned int)16, | 2831 | NULL, NULL, |
2812 | MHD_OPTION_NOTIFY_COMPLETED, &mhd_completed_cb, NULL, | 2832 | &create_response, hd, |
2813 | MHD_OPTION_NOTIFY_CONNECTION, &mhd_connection_cb, NULL, | 2833 | MHD_OPTION_CONNECTION_TIMEOUT, (unsigned |
2814 | MHD_OPTION_URI_LOG_CALLBACK, &mhd_log_callback, NULL, | 2834 | int) 16, |
2815 | MHD_OPTION_EXTERNAL_LOGGER, &mhd_error_log_callback, NULL, | 2835 | MHD_OPTION_NOTIFY_COMPLETED, &mhd_completed_cb, |
2816 | MHD_OPTION_HTTPS_MEM_KEY, pgc->key, | 2836 | NULL, |
2817 | MHD_OPTION_HTTPS_MEM_CERT, pgc->cert, | 2837 | MHD_OPTION_NOTIFY_CONNECTION, |
2818 | MHD_OPTION_END); | 2838 | &mhd_connection_cb, NULL, |
2839 | MHD_OPTION_URI_LOG_CALLBACK, &mhd_log_callback, | ||
2840 | NULL, | ||
2841 | MHD_OPTION_EXTERNAL_LOGGER, | ||
2842 | &mhd_error_log_callback, NULL, | ||
2843 | MHD_OPTION_HTTPS_MEM_KEY, pgc->key, | ||
2844 | MHD_OPTION_HTTPS_MEM_CERT, pgc->cert, | ||
2845 | MHD_OPTION_END); | ||
2819 | if (NULL == hd->daemon) | 2846 | if (NULL == hd->daemon) |
2820 | { | 2847 | { |
2821 | GNUNET_free(pgc); | 2848 | GNUNET_free (pgc); |
2822 | GNUNET_free(hd); | 2849 | GNUNET_free (hd); |
2823 | return NULL; | 2850 | return NULL; |
2824 | } | 2851 | } |
2825 | GNUNET_CONTAINER_DLL_insert(mhd_httpd_head, | 2852 | GNUNET_CONTAINER_DLL_insert (mhd_httpd_head, |
2826 | mhd_httpd_tail, | 2853 | mhd_httpd_tail, |
2827 | hd); | 2854 | hd); |
2828 | return hd; | 2855 | return hd; |
2829 | } | 2856 | } |
2830 | 2857 | ||
@@ -2837,12 +2864,12 @@ lookup_ssl_httpd(const char* domain) | |||
2837 | * @param cls the `struct Socks5Request *` | 2864 | * @param cls the `struct Socks5Request *` |
2838 | */ | 2865 | */ |
2839 | static void | 2866 | static void |
2840 | timeout_s5r_handshake(void *cls) | 2867 | timeout_s5r_handshake (void *cls) |
2841 | { | 2868 | { |
2842 | struct Socks5Request *s5r = cls; | 2869 | struct Socks5Request *s5r = cls; |
2843 | 2870 | ||
2844 | s5r->timeout_task = NULL; | 2871 | s5r->timeout_task = NULL; |
2845 | cleanup_s5r(s5r); | 2872 | cleanup_s5r (s5r); |
2846 | } | 2873 | } |
2847 | 2874 | ||
2848 | 2875 | ||
@@ -2855,7 +2882,7 @@ timeout_s5r_handshake(void *cls) | |||
2855 | * @param s5r socks request that has reached the final stage | 2882 | * @param s5r socks request that has reached the final stage |
2856 | */ | 2883 | */ |
2857 | static void | 2884 | static void |
2858 | setup_data_transfer(struct Socks5Request *s5r) | 2885 | setup_data_transfer (struct Socks5Request *s5r) |
2859 | { | 2886 | { |
2860 | struct MhdHttpList *hd; | 2887 | struct MhdHttpList *hd; |
2861 | int fd; | 2888 | int fd; |
@@ -2864,49 +2891,49 @@ setup_data_transfer(struct Socks5Request *s5r) | |||
2864 | char *domain; | 2891 | char *domain; |
2865 | 2892 | ||
2866 | if (GNUNET_YES == s5r->is_tls) | 2893 | if (GNUNET_YES == s5r->is_tls) |
2867 | { | 2894 | { |
2868 | GNUNET_asprintf(&domain, | 2895 | GNUNET_asprintf (&domain, |
2869 | "%s", | 2896 | "%s", |
2870 | s5r->domain); | ||
2871 | hd = lookup_ssl_httpd(domain); | ||
2872 | if (NULL == hd) | ||
2873 | { | ||
2874 | GNUNET_log(GNUNET_ERROR_TYPE_ERROR, | ||
2875 | _("Failed to start HTTPS server for `%s'\n"), | ||
2876 | s5r->domain); | 2897 | s5r->domain); |
2877 | cleanup_s5r(s5r); | 2898 | hd = lookup_ssl_httpd (domain); |
2878 | GNUNET_free(domain); | 2899 | if (NULL == hd) |
2879 | return; | 2900 | { |
2880 | } | 2901 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, |
2902 | _ ("Failed to start HTTPS server for `%s'\n"), | ||
2903 | s5r->domain); | ||
2904 | cleanup_s5r (s5r); | ||
2905 | GNUNET_free (domain); | ||
2906 | return; | ||
2881 | } | 2907 | } |
2908 | } | ||
2882 | else | 2909 | else |
2883 | { | 2910 | { |
2884 | domain = NULL; | 2911 | domain = NULL; |
2885 | GNUNET_assert(NULL != httpd); | 2912 | GNUNET_assert (NULL != httpd); |
2886 | hd = httpd; | 2913 | hd = httpd; |
2887 | } | 2914 | } |
2888 | fd = GNUNET_NETWORK_get_fd(s5r->sock); | 2915 | fd = GNUNET_NETWORK_get_fd (s5r->sock); |
2889 | addr = GNUNET_NETWORK_get_addr(s5r->sock); | 2916 | addr = GNUNET_NETWORK_get_addr (s5r->sock); |
2890 | len = GNUNET_NETWORK_get_addrlen(s5r->sock); | 2917 | len = GNUNET_NETWORK_get_addrlen (s5r->sock); |
2891 | s5r->state = SOCKS5_SOCKET_WITH_MHD; | 2918 | s5r->state = SOCKS5_SOCKET_WITH_MHD; |
2892 | if (MHD_YES != | 2919 | if (MHD_YES != |
2893 | MHD_add_connection(hd->daemon, | 2920 | MHD_add_connection (hd->daemon, |
2894 | fd, | 2921 | fd, |
2895 | addr, | 2922 | addr, |
2896 | len)) | 2923 | len)) |
2897 | { | 2924 | { |
2898 | GNUNET_log(GNUNET_ERROR_TYPE_WARNING, | 2925 | GNUNET_log (GNUNET_ERROR_TYPE_WARNING, |
2899 | _("Failed to pass client to MHD\n")); | 2926 | _ ("Failed to pass client to MHD\n")); |
2900 | cleanup_s5r(s5r); | 2927 | cleanup_s5r (s5r); |
2901 | GNUNET_free_non_null(domain); | 2928 | GNUNET_free_non_null (domain); |
2902 | return; | 2929 | return; |
2903 | } | 2930 | } |
2904 | s5r->hd = hd; | 2931 | s5r->hd = hd; |
2905 | schedule_httpd(hd); | 2932 | schedule_httpd (hd); |
2906 | s5r->timeout_task = GNUNET_SCHEDULER_add_delayed(HTTP_HANDSHAKE_TIMEOUT, | 2933 | s5r->timeout_task = GNUNET_SCHEDULER_add_delayed (HTTP_HANDSHAKE_TIMEOUT, |
2907 | &timeout_s5r_handshake, | 2934 | &timeout_s5r_handshake, |
2908 | s5r); | 2935 | s5r); |
2909 | GNUNET_free_non_null(domain); | 2936 | GNUNET_free_non_null (domain); |
2910 | } | 2937 | } |
2911 | 2938 | ||
2912 | 2939 | ||
@@ -2919,61 +2946,61 @@ setup_data_transfer(struct Socks5Request *s5r) | |||
2919 | * @param cls the closure with the `struct Socks5Request` | 2946 | * @param cls the closure with the `struct Socks5Request` |
2920 | */ | 2947 | */ |
2921 | static void | 2948 | static void |
2922 | do_write(void *cls) | 2949 | do_write (void *cls) |
2923 | { | 2950 | { |
2924 | struct Socks5Request *s5r = cls; | 2951 | struct Socks5Request *s5r = cls; |
2925 | ssize_t len; | 2952 | ssize_t len; |
2926 | 2953 | ||
2927 | s5r->wtask = NULL; | 2954 | s5r->wtask = NULL; |
2928 | len = GNUNET_NETWORK_socket_send(s5r->sock, | 2955 | len = GNUNET_NETWORK_socket_send (s5r->sock, |
2929 | s5r->wbuf, | 2956 | s5r->wbuf, |
2930 | s5r->wbuf_len); | 2957 | s5r->wbuf_len); |
2931 | if (len <= 0) | 2958 | if (len <= 0) |
2932 | { | 2959 | { |
2933 | /* write error: connection closed, shutdown, etc.; just clean up */ | 2960 | /* write error: connection closed, shutdown, etc.; just clean up */ |
2934 | GNUNET_log(GNUNET_ERROR_TYPE_ERROR, | 2961 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, |
2935 | "Write Error\n"); | 2962 | "Write Error\n"); |
2936 | cleanup_s5r(s5r); | 2963 | cleanup_s5r (s5r); |
2937 | return; | 2964 | return; |
2938 | } | 2965 | } |
2939 | memmove(s5r->wbuf, | 2966 | memmove (s5r->wbuf, |
2940 | &s5r->wbuf[len], | 2967 | &s5r->wbuf[len], |
2941 | s5r->wbuf_len - len); | 2968 | s5r->wbuf_len - len); |
2942 | s5r->wbuf_len -= len; | 2969 | s5r->wbuf_len -= len; |
2943 | if (s5r->wbuf_len > 0) | 2970 | if (s5r->wbuf_len > 0) |
2944 | { | 2971 | { |
2945 | /* not done writing */ | 2972 | /* not done writing */ |
2946 | s5r->wtask = | 2973 | s5r->wtask = |
2947 | GNUNET_SCHEDULER_add_write_net(GNUNET_TIME_UNIT_FOREVER_REL, | 2974 | GNUNET_SCHEDULER_add_write_net (GNUNET_TIME_UNIT_FOREVER_REL, |
2948 | s5r->sock, | 2975 | s5r->sock, |
2949 | &do_write, s5r); | 2976 | &do_write, s5r); |
2950 | return; | 2977 | return; |
2951 | } | 2978 | } |
2952 | 2979 | ||
2953 | /* we're done writing, continue with state machine! */ | 2980 | /* we're done writing, continue with state machine! */ |
2954 | 2981 | ||
2955 | switch (s5r->state) | 2982 | switch (s5r->state) |
2956 | { | 2983 | { |
2957 | case SOCKS5_INIT: | 2984 | case SOCKS5_INIT: |
2958 | GNUNET_assert(0); | 2985 | GNUNET_assert (0); |
2959 | break; | 2986 | break; |
2960 | 2987 | ||
2961 | case SOCKS5_REQUEST: | 2988 | case SOCKS5_REQUEST: |
2962 | GNUNET_assert(NULL != s5r->rtask); | 2989 | GNUNET_assert (NULL != s5r->rtask); |
2963 | break; | 2990 | break; |
2964 | 2991 | ||
2965 | case SOCKS5_DATA_TRANSFER: | 2992 | case SOCKS5_DATA_TRANSFER: |
2966 | setup_data_transfer(s5r); | 2993 | setup_data_transfer (s5r); |
2967 | return; | 2994 | return; |
2968 | 2995 | ||
2969 | case SOCKS5_WRITE_THEN_CLEANUP: | 2996 | case SOCKS5_WRITE_THEN_CLEANUP: |
2970 | cleanup_s5r(s5r); | 2997 | cleanup_s5r (s5r); |
2971 | return; | 2998 | return; |
2972 | 2999 | ||
2973 | default: | 3000 | default: |
2974 | GNUNET_break(0); | 3001 | GNUNET_break (0); |
2975 | break; | 3002 | break; |
2976 | } | 3003 | } |
2977 | } | 3004 | } |
2978 | 3005 | ||
2979 | 3006 | ||
@@ -2984,21 +3011,21 @@ do_write(void *cls) | |||
2984 | * @param sc status code to return | 3011 | * @param sc status code to return |
2985 | */ | 3012 | */ |
2986 | static void | 3013 | static void |
2987 | signal_socks_failure(struct Socks5Request *s5r, | 3014 | signal_socks_failure (struct Socks5Request *s5r, |
2988 | enum Socks5StatusCode sc) | 3015 | enum Socks5StatusCode sc) |
2989 | { | 3016 | { |
2990 | struct Socks5ServerResponseMessage *s_resp; | 3017 | struct Socks5ServerResponseMessage *s_resp; |
2991 | 3018 | ||
2992 | s_resp = (struct Socks5ServerResponseMessage *)&s5r->wbuf[s5r->wbuf_len]; | 3019 | s_resp = (struct Socks5ServerResponseMessage *) &s5r->wbuf[s5r->wbuf_len]; |
2993 | memset(s_resp, 0, sizeof(struct Socks5ServerResponseMessage)); | 3020 | memset (s_resp, 0, sizeof(struct Socks5ServerResponseMessage)); |
2994 | s_resp->version = SOCKS_VERSION_5; | 3021 | s_resp->version = SOCKS_VERSION_5; |
2995 | s_resp->reply = sc; | 3022 | s_resp->reply = sc; |
2996 | s5r->state = SOCKS5_WRITE_THEN_CLEANUP; | 3023 | s5r->state = SOCKS5_WRITE_THEN_CLEANUP; |
2997 | if (NULL != s5r->wtask) | 3024 | if (NULL != s5r->wtask) |
2998 | s5r->wtask = | 3025 | s5r->wtask = |
2999 | GNUNET_SCHEDULER_add_write_net(GNUNET_TIME_UNIT_FOREVER_REL, | 3026 | GNUNET_SCHEDULER_add_write_net (GNUNET_TIME_UNIT_FOREVER_REL, |
3000 | s5r->sock, | 3027 | s5r->sock, |
3001 | &do_write, s5r); | 3028 | &do_write, s5r); |
3002 | } | 3029 | } |
3003 | 3030 | ||
3004 | 3031 | ||
@@ -3008,26 +3035,26 @@ signal_socks_failure(struct Socks5Request *s5r, | |||
3008 | * @param s5r request to return success status message for | 3035 | * @param s5r request to return success status message for |
3009 | */ | 3036 | */ |
3010 | static void | 3037 | static void |
3011 | signal_socks_success(struct Socks5Request *s5r) | 3038 | signal_socks_success (struct Socks5Request *s5r) |
3012 | { | 3039 | { |
3013 | struct Socks5ServerResponseMessage *s_resp; | 3040 | struct Socks5ServerResponseMessage *s_resp; |
3014 | 3041 | ||
3015 | s_resp = (struct Socks5ServerResponseMessage *)&s5r->wbuf[s5r->wbuf_len]; | 3042 | s_resp = (struct Socks5ServerResponseMessage *) &s5r->wbuf[s5r->wbuf_len]; |
3016 | s_resp->version = SOCKS_VERSION_5; | 3043 | s_resp->version = SOCKS_VERSION_5; |
3017 | s_resp->reply = SOCKS5_STATUS_REQUEST_GRANTED; | 3044 | s_resp->reply = SOCKS5_STATUS_REQUEST_GRANTED; |
3018 | s_resp->reserved = 0; | 3045 | s_resp->reserved = 0; |
3019 | s_resp->addr_type = SOCKS5_AT_IPV4; | 3046 | s_resp->addr_type = SOCKS5_AT_IPV4; |
3020 | /* zero out IPv4 address and port */ | 3047 | /* zero out IPv4 address and port */ |
3021 | memset(&s_resp[1], | 3048 | memset (&s_resp[1], |
3022 | 0, | 3049 | 0, |
3023 | sizeof(struct in_addr) + sizeof(uint16_t)); | 3050 | sizeof(struct in_addr) + sizeof(uint16_t)); |
3024 | s5r->wbuf_len += sizeof(struct Socks5ServerResponseMessage) + | 3051 | s5r->wbuf_len += sizeof(struct Socks5ServerResponseMessage) |
3025 | sizeof(struct in_addr) + sizeof(uint16_t); | 3052 | + sizeof(struct in_addr) + sizeof(uint16_t); |
3026 | if (NULL == s5r->wtask) | 3053 | if (NULL == s5r->wtask) |
3027 | s5r->wtask = | 3054 | s5r->wtask = |
3028 | GNUNET_SCHEDULER_add_write_net(GNUNET_TIME_UNIT_FOREVER_REL, | 3055 | GNUNET_SCHEDULER_add_write_net (GNUNET_TIME_UNIT_FOREVER_REL, |
3029 | s5r->sock, | 3056 | s5r->sock, |
3030 | &do_write, s5r); | 3057 | &do_write, s5r); |
3031 | } | 3058 | } |
3032 | 3059 | ||
3033 | 3060 | ||
@@ -3040,10 +3067,10 @@ signal_socks_success(struct Socks5Request *s5r) | |||
3040 | * @param rd record data | 3067 | * @param rd record data |
3041 | */ | 3068 | */ |
3042 | static void | 3069 | static void |
3043 | handle_gns_result(void *cls, | 3070 | handle_gns_result (void *cls, |
3044 | int tld, | 3071 | int tld, |
3045 | uint32_t rd_count, | 3072 | uint32_t rd_count, |
3046 | const struct GNUNET_GNSRECORD_Data *rd) | 3073 | const struct GNUNET_GNSRECORD_Data *rd) |
3047 | { | 3074 | { |
3048 | struct Socks5Request *s5r = cls; | 3075 | struct Socks5Request *s5r = cls; |
3049 | const struct GNUNET_GNSRECORD_Data *r; | 3076 | const struct GNUNET_GNSRECORD_Data *r; |
@@ -3053,122 +3080,122 @@ handle_gns_result(void *cls, | |||
3053 | s5r->is_gns = tld; | 3080 | s5r->is_gns = tld; |
3054 | got_ip = GNUNET_NO; | 3081 | got_ip = GNUNET_NO; |
3055 | for (uint32_t i = 0; i < rd_count; i++) | 3082 | for (uint32_t i = 0; i < rd_count; i++) |
3083 | { | ||
3084 | r = &rd[i]; | ||
3085 | switch (r->record_type) | ||
3056 | { | 3086 | { |
3057 | r = &rd[i]; | 3087 | case GNUNET_DNSPARSER_TYPE_A: |
3058 | switch (r->record_type) | 3088 | { |
3059 | { | 3089 | struct sockaddr_in *in; |
3060 | case GNUNET_DNSPARSER_TYPE_A: | 3090 | |
3091 | if (sizeof(struct in_addr) != r->data_size) | ||
3061 | { | 3092 | { |
3062 | struct sockaddr_in *in; | 3093 | GNUNET_break_op (0); |
3063 | 3094 | break; | |
3064 | if (sizeof(struct in_addr) != r->data_size) | 3095 | } |
3065 | { | 3096 | if (GNUNET_YES == got_ip) |
3066 | GNUNET_break_op(0); | 3097 | break; |
3067 | break; | 3098 | if (GNUNET_OK != |
3068 | } | 3099 | GNUNET_NETWORK_test_pf (PF_INET)) |
3069 | if (GNUNET_YES == got_ip) | 3100 | break; |
3070 | break; | 3101 | got_ip = GNUNET_YES; |
3071 | if (GNUNET_OK != | 3102 | in = (struct sockaddr_in *) &s5r->destination_address; |
3072 | GNUNET_NETWORK_test_pf(PF_INET)) | 3103 | in->sin_family = AF_INET; |
3073 | break; | 3104 | GNUNET_memcpy (&in->sin_addr, |
3074 | got_ip = GNUNET_YES; | 3105 | r->data, |
3075 | in = (struct sockaddr_in *)&s5r->destination_address; | 3106 | r->data_size); |
3076 | in->sin_family = AF_INET; | 3107 | in->sin_port = htons (s5r->port); |
3077 | GNUNET_memcpy(&in->sin_addr, | ||
3078 | r->data, | ||
3079 | r->data_size); | ||
3080 | in->sin_port = htons(s5r->port); | ||
3081 | #if HAVE_SOCKADDR_IN_SIN_LEN | 3108 | #if HAVE_SOCKADDR_IN_SIN_LEN |
3082 | in->sin_len = sizeof(*in); | 3109 | in->sin_len = sizeof(*in); |
3083 | #endif | 3110 | #endif |
3084 | } | 3111 | } |
3085 | break; | 3112 | break; |
3113 | |||
3114 | case GNUNET_DNSPARSER_TYPE_AAAA: | ||
3115 | { | ||
3116 | struct sockaddr_in6 *in; | ||
3086 | 3117 | ||
3087 | case GNUNET_DNSPARSER_TYPE_AAAA: | 3118 | if (sizeof(struct in6_addr) != r->data_size) |
3088 | { | 3119 | { |
3089 | struct sockaddr_in6 *in; | 3120 | GNUNET_break_op (0); |
3090 | 3121 | break; | |
3091 | if (sizeof(struct in6_addr) != r->data_size) | 3122 | } |
3092 | { | 3123 | if (GNUNET_YES == got_ip) |
3093 | GNUNET_break_op(0); | 3124 | break; |
3094 | break; | 3125 | if (GNUNET_YES == disable_v6) |
3095 | } | 3126 | break; |
3096 | if (GNUNET_YES == got_ip) | 3127 | if (GNUNET_OK != |
3097 | break; | 3128 | GNUNET_NETWORK_test_pf (PF_INET6)) |
3098 | if (GNUNET_YES == disable_v6) | 3129 | break; |
3099 | break; | 3130 | /* FIXME: allow user to disable IPv6 per configuration option... */ |
3100 | if (GNUNET_OK != | 3131 | got_ip = GNUNET_YES; |
3101 | GNUNET_NETWORK_test_pf(PF_INET6)) | 3132 | in = (struct sockaddr_in6 *) &s5r->destination_address; |
3102 | break; | 3133 | in->sin6_family = AF_INET6; |
3103 | /* FIXME: allow user to disable IPv6 per configuration option... */ | 3134 | GNUNET_memcpy (&in->sin6_addr, |
3104 | got_ip = GNUNET_YES; | 3135 | r->data, |
3105 | in = (struct sockaddr_in6 *)&s5r->destination_address; | 3136 | r->data_size); |
3106 | in->sin6_family = AF_INET6; | 3137 | in->sin6_port = htons (s5r->port); |
3107 | GNUNET_memcpy(&in->sin6_addr, | ||
3108 | r->data, | ||
3109 | r->data_size); | ||
3110 | in->sin6_port = htons(s5r->port); | ||
3111 | #if HAVE_SOCKADDR_IN_SIN_LEN | 3138 | #if HAVE_SOCKADDR_IN_SIN_LEN |
3112 | in->sin6_len = sizeof(*in); | 3139 | in->sin6_len = sizeof(*in); |
3113 | #endif | 3140 | #endif |
3114 | } | 3141 | } |
3115 | break; | 3142 | break; |
3116 | 3143 | ||
3117 | case GNUNET_GNSRECORD_TYPE_VPN: | 3144 | case GNUNET_GNSRECORD_TYPE_VPN: |
3118 | GNUNET_break(0); /* should have been translated within GNS */ | 3145 | GNUNET_break (0); /* should have been translated within GNS */ |
3119 | break; | 3146 | break; |
3120 | 3147 | ||
3121 | case GNUNET_GNSRECORD_TYPE_LEHO: | 3148 | case GNUNET_GNSRECORD_TYPE_LEHO: |
3122 | GNUNET_free_non_null(s5r->leho); | 3149 | GNUNET_free_non_null (s5r->leho); |
3123 | s5r->leho = GNUNET_strndup(r->data, | 3150 | s5r->leho = GNUNET_strndup (r->data, |
3124 | r->data_size); | 3151 | r->data_size); |
3125 | break; | 3152 | break; |
3153 | |||
3154 | case GNUNET_GNSRECORD_TYPE_BOX: | ||
3155 | { | ||
3156 | const struct GNUNET_GNSRECORD_BoxRecord *box; | ||
3126 | 3157 | ||
3127 | case GNUNET_GNSRECORD_TYPE_BOX: | 3158 | if (r->data_size < sizeof(struct GNUNET_GNSRECORD_BoxRecord)) |
3128 | { | 3159 | { |
3129 | const struct GNUNET_GNSRECORD_BoxRecord *box; | 3160 | GNUNET_break_op (0); |
3130 | |||
3131 | if (r->data_size < sizeof(struct GNUNET_GNSRECORD_BoxRecord)) | ||
3132 | { | ||
3133 | GNUNET_break_op(0); | ||
3134 | break; | ||
3135 | } | ||
3136 | box = r->data; | ||
3137 | if ((ntohl(box->record_type) != GNUNET_DNSPARSER_TYPE_TLSA) || | ||
3138 | (ntohs(box->protocol) != IPPROTO_TCP) || | ||
3139 | (ntohs(box->service) != s5r->port)) | ||
3140 | break; /* BOX record does not apply */ | ||
3141 | if (s5r->num_danes >= MAX_DANES) | ||
3142 | { | ||
3143 | GNUNET_break(0); /* MAX_DANES too small */ | ||
3144 | break; | ||
3145 | } | ||
3146 | s5r->is_tls = GNUNET_YES; /* This should be TLS */ | ||
3147 | s5r->dane_data_len[s5r->num_danes] | ||
3148 | = r->data_size - sizeof(struct GNUNET_GNSRECORD_BoxRecord); | ||
3149 | s5r->dane_data[s5r->num_danes] | ||
3150 | = GNUNET_memdup(&box[1], | ||
3151 | s5r->dane_data_len[s5r->num_danes]); | ||
3152 | s5r->num_danes++; | ||
3153 | break; | 3161 | break; |
3154 | } | 3162 | } |
3155 | 3163 | box = r->data; | |
3156 | default: | 3164 | if ((ntohl (box->record_type) != GNUNET_DNSPARSER_TYPE_TLSA) || |
3157 | /* don't care */ | 3165 | (ntohs (box->protocol) != IPPROTO_TCP) || |
3166 | (ntohs (box->service) != s5r->port)) | ||
3167 | break; /* BOX record does not apply */ | ||
3168 | if (s5r->num_danes >= MAX_DANES) | ||
3169 | { | ||
3170 | GNUNET_break (0); /* MAX_DANES too small */ | ||
3158 | break; | 3171 | break; |
3159 | } | 3172 | } |
3173 | s5r->is_tls = GNUNET_YES; /* This should be TLS */ | ||
3174 | s5r->dane_data_len[s5r->num_danes] | ||
3175 | = r->data_size - sizeof(struct GNUNET_GNSRECORD_BoxRecord); | ||
3176 | s5r->dane_data[s5r->num_danes] | ||
3177 | = GNUNET_memdup (&box[1], | ||
3178 | s5r->dane_data_len[s5r->num_danes]); | ||
3179 | s5r->num_danes++; | ||
3180 | break; | ||
3181 | } | ||
3182 | |||
3183 | default: | ||
3184 | /* don't care */ | ||
3185 | break; | ||
3160 | } | 3186 | } |
3187 | } | ||
3161 | if ((GNUNET_YES != got_ip) && | 3188 | if ((GNUNET_YES != got_ip) && |
3162 | (GNUNET_YES == tld)) | 3189 | (GNUNET_YES == tld)) |
3163 | { | 3190 | { |
3164 | GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, | 3191 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
3165 | "Name resolution failed to yield useful IP address.\n"); | 3192 | "Name resolution failed to yield useful IP address.\n"); |
3166 | signal_socks_failure(s5r, | 3193 | signal_socks_failure (s5r, |
3167 | SOCKS5_STATUS_GENERAL_FAILURE); | 3194 | SOCKS5_STATUS_GENERAL_FAILURE); |
3168 | return; | 3195 | return; |
3169 | } | 3196 | } |
3170 | s5r->state = SOCKS5_DATA_TRANSFER; | 3197 | s5r->state = SOCKS5_DATA_TRANSFER; |
3171 | signal_socks_success(s5r); | 3198 | signal_socks_success (s5r); |
3172 | } | 3199 | } |
3173 | 3200 | ||
3174 | 3201 | ||
@@ -3179,13 +3206,13 @@ handle_gns_result(void *cls, | |||
3179 | * @param len number of bytes in read buffer to advance | 3206 | * @param len number of bytes in read buffer to advance |
3180 | */ | 3207 | */ |
3181 | static void | 3208 | static void |
3182 | clear_from_s5r_rbuf(struct Socks5Request *s5r, | 3209 | clear_from_s5r_rbuf (struct Socks5Request *s5r, |
3183 | size_t len) | 3210 | size_t len) |
3184 | { | 3211 | { |
3185 | GNUNET_assert(len <= s5r->rbuf_len); | 3212 | GNUNET_assert (len <= s5r->rbuf_len); |
3186 | memmove(s5r->rbuf, | 3213 | memmove (s5r->rbuf, |
3187 | &s5r->rbuf[len], | 3214 | &s5r->rbuf[len], |
3188 | s5r->rbuf_len - len); | 3215 | s5r->rbuf_len - len); |
3189 | s5r->rbuf_len -= len; | 3216 | s5r->rbuf_len -= len; |
3190 | } | 3217 | } |
3191 | 3218 | ||
@@ -3196,7 +3223,7 @@ clear_from_s5r_rbuf(struct Socks5Request *s5r, | |||
3196 | * @param cls the closure with the `struct Socks5Request` | 3223 | * @param cls the closure with the `struct Socks5Request` |
3197 | */ | 3224 | */ |
3198 | static void | 3225 | static void |
3199 | do_s5r_read(void *cls) | 3226 | do_s5r_read (void *cls) |
3200 | { | 3227 | { |
3201 | struct Socks5Request *s5r = cls; | 3228 | struct Socks5Request *s5r = cls; |
3202 | const struct Socks5ClientHelloMessage *c_hello; | 3229 | const struct Socks5ClientHelloMessage *c_hello; |
@@ -3207,196 +3234,198 @@ do_s5r_read(void *cls) | |||
3207 | const struct GNUNET_SCHEDULER_TaskContext *tc; | 3234 | const struct GNUNET_SCHEDULER_TaskContext *tc; |
3208 | 3235 | ||
3209 | s5r->rtask = NULL; | 3236 | s5r->rtask = NULL; |
3210 | tc = GNUNET_SCHEDULER_get_task_context(); | 3237 | tc = GNUNET_SCHEDULER_get_task_context (); |
3211 | if ((NULL != tc->read_ready) && | 3238 | if ((NULL != tc->read_ready) && |
3212 | (GNUNET_NETWORK_fdset_isset(tc->read_ready, | 3239 | (GNUNET_NETWORK_fdset_isset (tc->read_ready, |
3213 | s5r->sock))) | 3240 | s5r->sock))) |
3214 | { | 3241 | { |
3215 | rlen = GNUNET_NETWORK_socket_recv(s5r->sock, | 3242 | rlen = GNUNET_NETWORK_socket_recv (s5r->sock, |
3216 | &s5r->rbuf[s5r->rbuf_len], | 3243 | &s5r->rbuf[s5r->rbuf_len], |
3217 | sizeof(s5r->rbuf) - s5r->rbuf_len); | 3244 | sizeof(s5r->rbuf) - s5r->rbuf_len); |
3218 | if (rlen <= 0) | 3245 | if (rlen <= 0) |
3219 | { | 3246 | { |
3220 | GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, | 3247 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
3221 | "socks5 client disconnected.\n"); | 3248 | "socks5 client disconnected.\n"); |
3222 | cleanup_s5r(s5r); | 3249 | cleanup_s5r (s5r); |
3223 | return; | 3250 | return; |
3224 | } | ||
3225 | s5r->rbuf_len += rlen; | ||
3226 | } | 3251 | } |
3227 | s5r->rtask = GNUNET_SCHEDULER_add_read_net(GNUNET_TIME_UNIT_FOREVER_REL, | 3252 | s5r->rbuf_len += rlen; |
3228 | s5r->sock, | 3253 | } |
3229 | &do_s5r_read, s5r); | 3254 | s5r->rtask = GNUNET_SCHEDULER_add_read_net (GNUNET_TIME_UNIT_FOREVER_REL, |
3230 | GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, | 3255 | s5r->sock, |
3231 | "Processing %zu bytes of socks data in state %d\n", | 3256 | &do_s5r_read, s5r); |
3232 | s5r->rbuf_len, | 3257 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
3233 | s5r->state); | 3258 | "Processing %zu bytes of socks data in state %d\n", |
3259 | s5r->rbuf_len, | ||
3260 | s5r->state); | ||
3234 | switch (s5r->state) | 3261 | switch (s5r->state) |
3235 | { | 3262 | { |
3236 | case SOCKS5_INIT: | 3263 | case SOCKS5_INIT: |
3237 | c_hello = (const struct Socks5ClientHelloMessage*)&s5r->rbuf; | 3264 | c_hello = (const struct Socks5ClientHelloMessage*) &s5r->rbuf; |
3238 | if ((s5r->rbuf_len < sizeof(struct Socks5ClientHelloMessage)) || | 3265 | if ((s5r->rbuf_len < sizeof(struct Socks5ClientHelloMessage)) || |
3239 | (s5r->rbuf_len < sizeof(struct Socks5ClientHelloMessage) + c_hello->num_auth_methods)) | 3266 | (s5r->rbuf_len < sizeof(struct Socks5ClientHelloMessage) |
3240 | return; /* need more data */ | 3267 | + c_hello->num_auth_methods)) |
3241 | if (SOCKS_VERSION_5 != c_hello->version) | 3268 | return; /* need more data */ |
3242 | { | 3269 | if (SOCKS_VERSION_5 != c_hello->version) |
3243 | GNUNET_log(GNUNET_ERROR_TYPE_ERROR, | 3270 | { |
3244 | _("Unsupported socks version %d\n"), | 3271 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, |
3245 | (int)c_hello->version); | 3272 | _ ("Unsupported socks version %d\n"), |
3246 | cleanup_s5r(s5r); | 3273 | (int) c_hello->version); |
3247 | return; | 3274 | cleanup_s5r (s5r); |
3248 | } | ||
3249 | clear_from_s5r_rbuf(s5r, | ||
3250 | sizeof(struct Socks5ClientHelloMessage) + c_hello->num_auth_methods); | ||
3251 | GNUNET_assert(0 == s5r->wbuf_len); | ||
3252 | s_hello = (struct Socks5ServerHelloMessage *)&s5r->wbuf; | ||
3253 | s5r->wbuf_len = sizeof(struct Socks5ServerHelloMessage); | ||
3254 | s_hello->version = SOCKS_VERSION_5; | ||
3255 | s_hello->auth_method = SOCKS_AUTH_NONE; | ||
3256 | GNUNET_assert(NULL == s5r->wtask); | ||
3257 | s5r->wtask = GNUNET_SCHEDULER_add_write_net(GNUNET_TIME_UNIT_FOREVER_REL, | ||
3258 | s5r->sock, | ||
3259 | &do_write, s5r); | ||
3260 | s5r->state = SOCKS5_REQUEST; | ||
3261 | return; | 3275 | return; |
3276 | } | ||
3277 | clear_from_s5r_rbuf (s5r, | ||
3278 | sizeof(struct Socks5ClientHelloMessage) | ||
3279 | + c_hello->num_auth_methods); | ||
3280 | GNUNET_assert (0 == s5r->wbuf_len); | ||
3281 | s_hello = (struct Socks5ServerHelloMessage *) &s5r->wbuf; | ||
3282 | s5r->wbuf_len = sizeof(struct Socks5ServerHelloMessage); | ||
3283 | s_hello->version = SOCKS_VERSION_5; | ||
3284 | s_hello->auth_method = SOCKS_AUTH_NONE; | ||
3285 | GNUNET_assert (NULL == s5r->wtask); | ||
3286 | s5r->wtask = GNUNET_SCHEDULER_add_write_net (GNUNET_TIME_UNIT_FOREVER_REL, | ||
3287 | s5r->sock, | ||
3288 | &do_write, s5r); | ||
3289 | s5r->state = SOCKS5_REQUEST; | ||
3290 | return; | ||
3262 | 3291 | ||
3263 | case SOCKS5_REQUEST: | 3292 | case SOCKS5_REQUEST: |
3264 | c_req = (const struct Socks5ClientRequestMessage *)&s5r->rbuf; | 3293 | c_req = (const struct Socks5ClientRequestMessage *) &s5r->rbuf; |
3265 | if (s5r->rbuf_len < sizeof(struct Socks5ClientRequestMessage)) | 3294 | if (s5r->rbuf_len < sizeof(struct Socks5ClientRequestMessage)) |
3266 | return; | 3295 | return; |
3267 | switch (c_req->command) | 3296 | switch (c_req->command) |
3268 | { | 3297 | { |
3269 | case SOCKS5_CMD_TCP_STREAM: | 3298 | case SOCKS5_CMD_TCP_STREAM: |
3270 | /* handled below */ | 3299 | /* handled below */ |
3271 | break; | 3300 | break; |
3272 | 3301 | ||
3273 | default: | 3302 | default: |
3274 | GNUNET_log(GNUNET_ERROR_TYPE_ERROR, | 3303 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, |
3275 | _("Unsupported socks command %d\n"), | 3304 | _ ("Unsupported socks command %d\n"), |
3276 | (int)c_req->command); | 3305 | (int) c_req->command); |
3277 | signal_socks_failure(s5r, | 3306 | signal_socks_failure (s5r, |
3278 | SOCKS5_STATUS_COMMAND_NOT_SUPPORTED); | 3307 | SOCKS5_STATUS_COMMAND_NOT_SUPPORTED); |
3279 | return; | 3308 | return; |
3280 | } | 3309 | } |
3281 | switch (c_req->addr_type) | 3310 | switch (c_req->addr_type) |
3282 | { | 3311 | { |
3283 | case SOCKS5_AT_IPV4: | 3312 | case SOCKS5_AT_IPV4: |
3284 | { | 3313 | { |
3285 | const struct in_addr *v4 = (const struct in_addr *)&c_req[1]; | 3314 | const struct in_addr *v4 = (const struct in_addr *) &c_req[1]; |
3286 | const uint16_t *port = (const uint16_t *)&v4[1]; | 3315 | const uint16_t *port = (const uint16_t *) &v4[1]; |
3287 | struct sockaddr_in *in; | 3316 | struct sockaddr_in *in; |
3288 | 3317 | ||
3289 | s5r->port = ntohs(*port); | 3318 | s5r->port = ntohs (*port); |
3290 | alen = sizeof(struct in_addr); | 3319 | alen = sizeof(struct in_addr); |
3291 | if (s5r->rbuf_len < sizeof(struct Socks5ClientRequestMessage) + | 3320 | if (s5r->rbuf_len < sizeof(struct Socks5ClientRequestMessage) |
3292 | alen + sizeof(uint16_t)) | 3321 | + alen + sizeof(uint16_t)) |
3293 | return; /* need more data */ | 3322 | return; /* need more data */ |
3294 | in = (struct sockaddr_in *)&s5r->destination_address; | 3323 | in = (struct sockaddr_in *) &s5r->destination_address; |
3295 | in->sin_family = AF_INET; | 3324 | in->sin_family = AF_INET; |
3296 | in->sin_addr = *v4; | 3325 | in->sin_addr = *v4; |
3297 | in->sin_port = *port; | 3326 | in->sin_port = *port; |
3298 | #if HAVE_SOCKADDR_IN_SIN_LEN | 3327 | #if HAVE_SOCKADDR_IN_SIN_LEN |
3299 | in->sin_len = sizeof(*in); | 3328 | in->sin_len = sizeof(*in); |
3300 | #endif | 3329 | #endif |
3301 | s5r->state = SOCKS5_DATA_TRANSFER; | 3330 | s5r->state = SOCKS5_DATA_TRANSFER; |
3302 | } | 3331 | } |
3303 | break; | 3332 | break; |
3304 | 3333 | ||
3305 | case SOCKS5_AT_IPV6: | 3334 | case SOCKS5_AT_IPV6: |
3306 | { | 3335 | { |
3307 | const struct in6_addr *v6 = (const struct in6_addr *)&c_req[1]; | 3336 | const struct in6_addr *v6 = (const struct in6_addr *) &c_req[1]; |
3308 | const uint16_t *port = (const uint16_t *)&v6[1]; | 3337 | const uint16_t *port = (const uint16_t *) &v6[1]; |
3309 | struct sockaddr_in6 *in; | 3338 | struct sockaddr_in6 *in; |
3310 | 3339 | ||
3311 | s5r->port = ntohs(*port); | 3340 | s5r->port = ntohs (*port); |
3312 | alen = sizeof(struct in6_addr); | 3341 | alen = sizeof(struct in6_addr); |
3313 | if (s5r->rbuf_len < sizeof(struct Socks5ClientRequestMessage) + | 3342 | if (s5r->rbuf_len < sizeof(struct Socks5ClientRequestMessage) |
3314 | alen + sizeof(uint16_t)) | 3343 | + alen + sizeof(uint16_t)) |
3315 | return; /* need more data */ | 3344 | return; /* need more data */ |
3316 | in = (struct sockaddr_in6 *)&s5r->destination_address; | 3345 | in = (struct sockaddr_in6 *) &s5r->destination_address; |
3317 | in->sin6_family = AF_INET6; | 3346 | in->sin6_family = AF_INET6; |
3318 | in->sin6_addr = *v6; | 3347 | in->sin6_addr = *v6; |
3319 | in->sin6_port = *port; | 3348 | in->sin6_port = *port; |
3320 | #if HAVE_SOCKADDR_IN_SIN_LEN | 3349 | #if HAVE_SOCKADDR_IN_SIN_LEN |
3321 | in->sin6_len = sizeof(*in); | 3350 | in->sin6_len = sizeof(*in); |
3322 | #endif | 3351 | #endif |
3323 | s5r->state = SOCKS5_DATA_TRANSFER; | 3352 | s5r->state = SOCKS5_DATA_TRANSFER; |
3324 | } | 3353 | } |
3325 | break; | 3354 | break; |
3326 | 3355 | ||
3327 | case SOCKS5_AT_DOMAINNAME: | 3356 | case SOCKS5_AT_DOMAINNAME: |
3328 | { | 3357 | { |
3329 | const uint8_t *dom_len; | 3358 | const uint8_t *dom_len; |
3330 | const char *dom_name; | 3359 | const char *dom_name; |
3331 | const uint16_t *port; | 3360 | const uint16_t *port; |
3332 | 3361 | ||
3333 | dom_len = (const uint8_t *)&c_req[1]; | 3362 | dom_len = (const uint8_t *) &c_req[1]; |
3334 | alen = *dom_len + 1; | 3363 | alen = *dom_len + 1; |
3335 | if (s5r->rbuf_len < sizeof(struct Socks5ClientRequestMessage) + | 3364 | if (s5r->rbuf_len < sizeof(struct Socks5ClientRequestMessage) |
3336 | alen + sizeof(uint16_t)) | 3365 | + alen + sizeof(uint16_t)) |
3337 | return; /* need more data */ | 3366 | return; /* need more data */ |
3338 | dom_name = (const char *)&dom_len[1]; | 3367 | dom_name = (const char *) &dom_len[1]; |
3339 | port = (const uint16_t*)&dom_name[*dom_len]; | 3368 | port = (const uint16_t*) &dom_name[*dom_len]; |
3340 | s5r->domain = GNUNET_strndup(dom_name, | 3369 | s5r->domain = GNUNET_strndup (dom_name, |
3341 | *dom_len); | 3370 | *dom_len); |
3342 | GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, | 3371 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
3343 | "Requested connection is to %s:%d\n", | 3372 | "Requested connection is to %s:%d\n", |
3344 | //(HTTPS_PORT == s5r->port) ? "s" : "", | 3373 | // (HTTPS_PORT == s5r->port) ? "s" : "", |
3345 | s5r->domain, | 3374 | s5r->domain, |
3346 | ntohs(*port)); | 3375 | ntohs (*port)); |
3347 | s5r->state = SOCKS5_RESOLVING; | 3376 | s5r->state = SOCKS5_RESOLVING; |
3348 | s5r->port = ntohs(*port); | 3377 | s5r->port = ntohs (*port); |
3349 | s5r->is_tls = (HTTPS_PORT == s5r->port) ? GNUNET_YES : GNUNET_NO; | 3378 | s5r->is_tls = (HTTPS_PORT == s5r->port) ? GNUNET_YES : GNUNET_NO; |
3350 | s5r->gns_lookup = GNUNET_GNS_lookup_with_tld(gns_handle, | 3379 | s5r->gns_lookup = GNUNET_GNS_lookup_with_tld (gns_handle, |
3351 | s5r->domain, | 3380 | s5r->domain, |
3352 | GNUNET_DNSPARSER_TYPE_A, | 3381 | GNUNET_DNSPARSER_TYPE_A, |
3353 | GNUNET_NO /* only cached */, | 3382 | GNUNET_NO /* only cached */, |
3354 | &handle_gns_result, | 3383 | &handle_gns_result, |
3355 | s5r); | 3384 | s5r); |
3356 | break; | 3385 | break; |
3357 | } | 3386 | } |
3358 | 3387 | ||
3359 | default: | 3388 | default: |
3360 | GNUNET_log(GNUNET_ERROR_TYPE_ERROR, | 3389 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, |
3361 | _("Unsupported socks address type %d\n"), | 3390 | _ ("Unsupported socks address type %d\n"), |
3362 | (int)c_req->addr_type); | 3391 | (int) c_req->addr_type); |
3363 | signal_socks_failure(s5r, | 3392 | signal_socks_failure (s5r, |
3364 | SOCKS5_STATUS_ADDRESS_TYPE_NOT_SUPPORTED); | 3393 | SOCKS5_STATUS_ADDRESS_TYPE_NOT_SUPPORTED); |
3365 | return; | ||
3366 | } | ||
3367 | clear_from_s5r_rbuf(s5r, | ||
3368 | sizeof(struct Socks5ClientRequestMessage) + | ||
3369 | alen + sizeof(uint16_t)); | ||
3370 | if (0 != s5r->rbuf_len) | ||
3371 | { | ||
3372 | /* read more bytes than healthy, why did the client send more!? */ | ||
3373 | GNUNET_break_op(0); | ||
3374 | signal_socks_failure(s5r, | ||
3375 | SOCKS5_STATUS_GENERAL_FAILURE); | ||
3376 | return; | ||
3377 | } | ||
3378 | if (SOCKS5_DATA_TRANSFER == s5r->state) | ||
3379 | { | ||
3380 | /* if we are not waiting for GNS resolution, signal success */ | ||
3381 | signal_socks_success(s5r); | ||
3382 | } | ||
3383 | /* We are done reading right now */ | ||
3384 | GNUNET_SCHEDULER_cancel(s5r->rtask); | ||
3385 | s5r->rtask = NULL; | ||
3386 | return; | 3394 | return; |
3387 | 3395 | } | |
3388 | case SOCKS5_RESOLVING: | 3396 | clear_from_s5r_rbuf (s5r, |
3389 | GNUNET_assert(0); | 3397 | sizeof(struct Socks5ClientRequestMessage) |
3398 | + alen + sizeof(uint16_t)); | ||
3399 | if (0 != s5r->rbuf_len) | ||
3400 | { | ||
3401 | /* read more bytes than healthy, why did the client send more!? */ | ||
3402 | GNUNET_break_op (0); | ||
3403 | signal_socks_failure (s5r, | ||
3404 | SOCKS5_STATUS_GENERAL_FAILURE); | ||
3390 | return; | 3405 | return; |
3406 | } | ||
3407 | if (SOCKS5_DATA_TRANSFER == s5r->state) | ||
3408 | { | ||
3409 | /* if we are not waiting for GNS resolution, signal success */ | ||
3410 | signal_socks_success (s5r); | ||
3411 | } | ||
3412 | /* We are done reading right now */ | ||
3413 | GNUNET_SCHEDULER_cancel (s5r->rtask); | ||
3414 | s5r->rtask = NULL; | ||
3415 | return; | ||
3391 | 3416 | ||
3392 | case SOCKS5_DATA_TRANSFER: | 3417 | case SOCKS5_RESOLVING: |
3393 | GNUNET_assert(0); | 3418 | GNUNET_assert (0); |
3394 | return; | 3419 | return; |
3395 | 3420 | ||
3396 | default: | 3421 | case SOCKS5_DATA_TRANSFER: |
3397 | GNUNET_assert(0); | 3422 | GNUNET_assert (0); |
3398 | return; | 3423 | return; |
3399 | } | 3424 | |
3425 | default: | ||
3426 | GNUNET_assert (0); | ||
3427 | return; | ||
3428 | } | ||
3400 | } | 3429 | } |
3401 | 3430 | ||
3402 | 3431 | ||
@@ -3407,46 +3436,46 @@ do_s5r_read(void *cls) | |||
3407 | * @param tc the scheduler context | 3436 | * @param tc the scheduler context |
3408 | */ | 3437 | */ |
3409 | static void | 3438 | static void |
3410 | do_accept(void *cls) | 3439 | do_accept (void *cls) |
3411 | { | 3440 | { |
3412 | struct GNUNET_NETWORK_Handle *lsock = cls; | 3441 | struct GNUNET_NETWORK_Handle *lsock = cls; |
3413 | struct GNUNET_NETWORK_Handle *s; | 3442 | struct GNUNET_NETWORK_Handle *s; |
3414 | struct Socks5Request *s5r; | 3443 | struct Socks5Request *s5r; |
3415 | 3444 | ||
3416 | GNUNET_assert(NULL != lsock); | 3445 | GNUNET_assert (NULL != lsock); |
3417 | if (lsock == lsock4) | 3446 | if (lsock == lsock4) |
3418 | ltask4 = GNUNET_SCHEDULER_add_read_net(GNUNET_TIME_UNIT_FOREVER_REL, | 3447 | ltask4 = GNUNET_SCHEDULER_add_read_net (GNUNET_TIME_UNIT_FOREVER_REL, |
3419 | lsock, | 3448 | lsock, |
3420 | &do_accept, | 3449 | &do_accept, |
3421 | lsock); | 3450 | lsock); |
3422 | else if (lsock == lsock6) | 3451 | else if (lsock == lsock6) |
3423 | ltask6 = GNUNET_SCHEDULER_add_read_net(GNUNET_TIME_UNIT_FOREVER_REL, | 3452 | ltask6 = GNUNET_SCHEDULER_add_read_net (GNUNET_TIME_UNIT_FOREVER_REL, |
3424 | lsock, | 3453 | lsock, |
3425 | &do_accept, | 3454 | &do_accept, |
3426 | lsock); | 3455 | lsock); |
3427 | else | 3456 | else |
3428 | GNUNET_assert(0); | 3457 | GNUNET_assert (0); |
3429 | s = GNUNET_NETWORK_socket_accept(lsock, | 3458 | s = GNUNET_NETWORK_socket_accept (lsock, |
3430 | NULL, | 3459 | NULL, |
3431 | NULL); | 3460 | NULL); |
3432 | if (NULL == s) | 3461 | if (NULL == s) |
3433 | { | 3462 | { |
3434 | GNUNET_log_strerror(GNUNET_ERROR_TYPE_ERROR, | 3463 | GNUNET_log_strerror (GNUNET_ERROR_TYPE_ERROR, |
3435 | "accept"); | 3464 | "accept"); |
3436 | return; | 3465 | return; |
3437 | } | 3466 | } |
3438 | GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, | 3467 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
3439 | "Got an inbound connection, waiting for data\n"); | 3468 | "Got an inbound connection, waiting for data\n"); |
3440 | s5r = GNUNET_new(struct Socks5Request); | 3469 | s5r = GNUNET_new (struct Socks5Request); |
3441 | GNUNET_CONTAINER_DLL_insert(s5r_head, | 3470 | GNUNET_CONTAINER_DLL_insert (s5r_head, |
3442 | s5r_tail, | 3471 | s5r_tail, |
3443 | s5r); | 3472 | s5r); |
3444 | s5r->sock = s; | 3473 | s5r->sock = s; |
3445 | s5r->state = SOCKS5_INIT; | 3474 | s5r->state = SOCKS5_INIT; |
3446 | s5r->rtask = GNUNET_SCHEDULER_add_read_net(GNUNET_TIME_UNIT_FOREVER_REL, | 3475 | s5r->rtask = GNUNET_SCHEDULER_add_read_net (GNUNET_TIME_UNIT_FOREVER_REL, |
3447 | s5r->sock, | 3476 | s5r->sock, |
3448 | &do_s5r_read, | 3477 | &do_s5r_read, |
3449 | s5r); | 3478 | s5r); |
3450 | } | 3479 | } |
3451 | 3480 | ||
3452 | 3481 | ||
@@ -3459,63 +3488,63 @@ do_accept(void *cls) | |||
3459 | * @param cls closure | 3488 | * @param cls closure |
3460 | */ | 3489 | */ |
3461 | static void | 3490 | static void |
3462 | do_shutdown(void *cls) | 3491 | do_shutdown (void *cls) |
3463 | { | 3492 | { |
3464 | GNUNET_log(GNUNET_ERROR_TYPE_INFO, | 3493 | GNUNET_log (GNUNET_ERROR_TYPE_INFO, |
3465 | "Shutting down...\n"); | 3494 | "Shutting down...\n"); |
3466 | /* MHD requires resuming before destroying the daemons */ | 3495 | /* MHD requires resuming before destroying the daemons */ |
3467 | for (struct Socks5Request *s5r = s5r_head; | 3496 | for (struct Socks5Request *s5r = s5r_head; |
3468 | NULL != s5r; | 3497 | NULL != s5r; |
3469 | s5r = s5r->next) | 3498 | s5r = s5r->next) |
3499 | { | ||
3500 | if (s5r->suspended) | ||
3470 | { | 3501 | { |
3471 | if (s5r->suspended) | 3502 | s5r->suspended = GNUNET_NO; |
3472 | { | 3503 | MHD_resume_connection (s5r->con); |
3473 | s5r->suspended = GNUNET_NO; | ||
3474 | MHD_resume_connection(s5r->con); | ||
3475 | } | ||
3476 | } | 3504 | } |
3505 | } | ||
3477 | while (NULL != mhd_httpd_head) | 3506 | while (NULL != mhd_httpd_head) |
3478 | kill_httpd(mhd_httpd_head); | 3507 | kill_httpd (mhd_httpd_head); |
3479 | while (NULL != s5r_head) | 3508 | while (NULL != s5r_head) |
3480 | cleanup_s5r(s5r_head); | 3509 | cleanup_s5r (s5r_head); |
3481 | if (NULL != lsock4) | 3510 | if (NULL != lsock4) |
3482 | { | 3511 | { |
3483 | GNUNET_NETWORK_socket_close(lsock4); | 3512 | GNUNET_NETWORK_socket_close (lsock4); |
3484 | lsock4 = NULL; | 3513 | lsock4 = NULL; |
3485 | } | 3514 | } |
3486 | if (NULL != lsock6) | 3515 | if (NULL != lsock6) |
3487 | { | 3516 | { |
3488 | GNUNET_NETWORK_socket_close(lsock6); | 3517 | GNUNET_NETWORK_socket_close (lsock6); |
3489 | lsock6 = NULL; | 3518 | lsock6 = NULL; |
3490 | } | 3519 | } |
3491 | if (NULL != curl_multi) | 3520 | if (NULL != curl_multi) |
3492 | { | 3521 | { |
3493 | curl_multi_cleanup(curl_multi); | 3522 | curl_multi_cleanup (curl_multi); |
3494 | curl_multi = NULL; | 3523 | curl_multi = NULL; |
3495 | } | 3524 | } |
3496 | if (NULL != gns_handle) | 3525 | if (NULL != gns_handle) |
3497 | { | 3526 | { |
3498 | GNUNET_GNS_disconnect(gns_handle); | 3527 | GNUNET_GNS_disconnect (gns_handle); |
3499 | gns_handle = NULL; | 3528 | gns_handle = NULL; |
3500 | } | 3529 | } |
3501 | if (NULL != curl_download_task) | 3530 | if (NULL != curl_download_task) |
3502 | { | 3531 | { |
3503 | GNUNET_SCHEDULER_cancel(curl_download_task); | 3532 | GNUNET_SCHEDULER_cancel (curl_download_task); |
3504 | curl_download_task = NULL; | 3533 | curl_download_task = NULL; |
3505 | } | 3534 | } |
3506 | if (NULL != ltask4) | 3535 | if (NULL != ltask4) |
3507 | { | 3536 | { |
3508 | GNUNET_SCHEDULER_cancel(ltask4); | 3537 | GNUNET_SCHEDULER_cancel (ltask4); |
3509 | ltask4 = NULL; | 3538 | ltask4 = NULL; |
3510 | } | 3539 | } |
3511 | if (NULL != ltask6) | 3540 | if (NULL != ltask6) |
3512 | { | 3541 | { |
3513 | GNUNET_SCHEDULER_cancel(ltask6); | 3542 | GNUNET_SCHEDULER_cancel (ltask6); |
3514 | ltask6 = NULL; | 3543 | ltask6 = NULL; |
3515 | } | 3544 | } |
3516 | gnutls_x509_crt_deinit(proxy_ca.cert); | 3545 | gnutls_x509_crt_deinit (proxy_ca.cert); |
3517 | gnutls_x509_privkey_deinit(proxy_ca.key); | 3546 | gnutls_x509_privkey_deinit (proxy_ca.key); |
3518 | gnutls_global_deinit(); | 3547 | gnutls_global_deinit (); |
3519 | } | 3548 | } |
3520 | 3549 | ||
3521 | 3550 | ||
@@ -3525,34 +3554,34 @@ do_shutdown(void *cls) | |||
3525 | * @return NULL on error | 3554 | * @return NULL on error |
3526 | */ | 3555 | */ |
3527 | static struct GNUNET_NETWORK_Handle * | 3556 | static struct GNUNET_NETWORK_Handle * |
3528 | bind_v4() | 3557 | bind_v4 () |
3529 | { | 3558 | { |
3530 | struct GNUNET_NETWORK_Handle *ls; | 3559 | struct GNUNET_NETWORK_Handle *ls; |
3531 | struct sockaddr_in sa4; | 3560 | struct sockaddr_in sa4; |
3532 | int eno; | 3561 | int eno; |
3533 | 3562 | ||
3534 | memset(&sa4, 0, sizeof(sa4)); | 3563 | memset (&sa4, 0, sizeof(sa4)); |
3535 | sa4.sin_family = AF_INET; | 3564 | sa4.sin_family = AF_INET; |
3536 | sa4.sin_port = htons(port); | 3565 | sa4.sin_port = htons (port); |
3537 | sa4.sin_addr.s_addr = address; | 3566 | sa4.sin_addr.s_addr = address; |
3538 | #if HAVE_SOCKADDR_IN_SIN_LEN | 3567 | #if HAVE_SOCKADDR_IN_SIN_LEN |
3539 | sa4.sin_len = sizeof(sa4); | 3568 | sa4.sin_len = sizeof(sa4); |
3540 | #endif | 3569 | #endif |
3541 | ls = GNUNET_NETWORK_socket_create(AF_INET, | 3570 | ls = GNUNET_NETWORK_socket_create (AF_INET, |
3542 | SOCK_STREAM, | 3571 | SOCK_STREAM, |
3543 | 0); | 3572 | 0); |
3544 | if (NULL == ls) | 3573 | if (NULL == ls) |
3545 | return NULL; | 3574 | return NULL; |
3546 | if (GNUNET_OK != | 3575 | if (GNUNET_OK != |
3547 | GNUNET_NETWORK_socket_bind(ls, | 3576 | GNUNET_NETWORK_socket_bind (ls, |
3548 | (const struct sockaddr *)&sa4, | 3577 | (const struct sockaddr *) &sa4, |
3549 | sizeof(sa4))) | 3578 | sizeof(sa4))) |
3550 | { | 3579 | { |
3551 | eno = errno; | 3580 | eno = errno; |
3552 | GNUNET_NETWORK_socket_close(ls); | 3581 | GNUNET_NETWORK_socket_close (ls); |
3553 | errno = eno; | 3582 | errno = eno; |
3554 | return NULL; | 3583 | return NULL; |
3555 | } | 3584 | } |
3556 | return ls; | 3585 | return ls; |
3557 | } | 3586 | } |
3558 | 3587 | ||
@@ -3563,34 +3592,34 @@ bind_v4() | |||
3563 | * @return NULL on error | 3592 | * @return NULL on error |
3564 | */ | 3593 | */ |
3565 | static struct GNUNET_NETWORK_Handle * | 3594 | static struct GNUNET_NETWORK_Handle * |
3566 | bind_v6() | 3595 | bind_v6 () |
3567 | { | 3596 | { |
3568 | struct GNUNET_NETWORK_Handle *ls; | 3597 | struct GNUNET_NETWORK_Handle *ls; |
3569 | struct sockaddr_in6 sa6; | 3598 | struct sockaddr_in6 sa6; |
3570 | int eno; | 3599 | int eno; |
3571 | 3600 | ||
3572 | memset(&sa6, 0, sizeof(sa6)); | 3601 | memset (&sa6, 0, sizeof(sa6)); |
3573 | sa6.sin6_family = AF_INET6; | 3602 | sa6.sin6_family = AF_INET6; |
3574 | sa6.sin6_port = htons(port); | 3603 | sa6.sin6_port = htons (port); |
3575 | sa6.sin6_addr = address6; | 3604 | sa6.sin6_addr = address6; |
3576 | #if HAVE_SOCKADDR_IN_SIN_LEN | 3605 | #if HAVE_SOCKADDR_IN_SIN_LEN |
3577 | sa6.sin6_len = sizeof(sa6); | 3606 | sa6.sin6_len = sizeof(sa6); |
3578 | #endif | 3607 | #endif |
3579 | ls = GNUNET_NETWORK_socket_create(AF_INET6, | 3608 | ls = GNUNET_NETWORK_socket_create (AF_INET6, |
3580 | SOCK_STREAM, | 3609 | SOCK_STREAM, |
3581 | 0); | 3610 | 0); |
3582 | if (NULL == ls) | 3611 | if (NULL == ls) |
3583 | return NULL; | 3612 | return NULL; |
3584 | if (GNUNET_OK != | 3613 | if (GNUNET_OK != |
3585 | GNUNET_NETWORK_socket_bind(ls, | 3614 | GNUNET_NETWORK_socket_bind (ls, |
3586 | (const struct sockaddr *)&sa6, | 3615 | (const struct sockaddr *) &sa6, |
3587 | sizeof(sa6))) | 3616 | sizeof(sa6))) |
3588 | { | 3617 | { |
3589 | eno = errno; | 3618 | eno = errno; |
3590 | GNUNET_NETWORK_socket_close(ls); | 3619 | GNUNET_NETWORK_socket_close (ls); |
3591 | errno = eno; | 3620 | errno = eno; |
3592 | return NULL; | 3621 | return NULL; |
3593 | } | 3622 | } |
3594 | return ls; | 3623 | return ls; |
3595 | } | 3624 | } |
3596 | 3625 | ||
@@ -3604,211 +3633,216 @@ bind_v6() | |||
3604 | * @param c configuration | 3633 | * @param c configuration |
3605 | */ | 3634 | */ |
3606 | static void | 3635 | static void |
3607 | run(void *cls, | 3636 | run (void *cls, |
3608 | char *const *args, | 3637 | char *const *args, |
3609 | const char *cfgfile, | 3638 | const char *cfgfile, |
3610 | const struct GNUNET_CONFIGURATION_Handle *c) | 3639 | const struct GNUNET_CONFIGURATION_Handle *c) |
3611 | { | 3640 | { |
3612 | char* cafile_cfg = NULL; | 3641 | char*cafile_cfg = NULL; |
3613 | char* cafile; | 3642 | char*cafile; |
3614 | char* addr_str; | 3643 | char*addr_str; |
3615 | struct MhdHttpList *hd; | 3644 | struct MhdHttpList *hd; |
3616 | 3645 | ||
3617 | cfg = c; | 3646 | cfg = c; |
3618 | 3647 | ||
3619 | /* Get address to bind to */ | 3648 | /* Get address to bind to */ |
3620 | if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_string(cfg, "gns-proxy", | 3649 | if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_string (cfg, "gns-proxy", |
3621 | "BIND_TO", | 3650 | "BIND_TO", |
3622 | &addr_str)) | 3651 | &addr_str)) |
3623 | { | 3652 | { |
3624 | //No address specified | 3653 | // No address specified |
3625 | GNUNET_log(GNUNET_ERROR_TYPE_ERROR, | 3654 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, |
3626 | "Don't know what to bind to...\n"); | 3655 | "Don't know what to bind to...\n"); |
3627 | GNUNET_free(addr_str); | 3656 | GNUNET_free (addr_str); |
3628 | GNUNET_SCHEDULER_shutdown(); | 3657 | GNUNET_SCHEDULER_shutdown (); |
3629 | return; | 3658 | return; |
3630 | } | 3659 | } |
3631 | if (1 != inet_pton(AF_INET, addr_str, &address)) | 3660 | if (1 != inet_pton (AF_INET, addr_str, &address)) |
3632 | { | 3661 | { |
3633 | GNUNET_log(GNUNET_ERROR_TYPE_ERROR, | 3662 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, |
3634 | "Unable to parse address %s\n", | 3663 | "Unable to parse address %s\n", |
3635 | addr_str); | 3664 | addr_str); |
3636 | GNUNET_free(addr_str); | 3665 | GNUNET_free (addr_str); |
3637 | GNUNET_SCHEDULER_shutdown(); | 3666 | GNUNET_SCHEDULER_shutdown (); |
3638 | return; | 3667 | return; |
3639 | } | 3668 | } |
3640 | GNUNET_free(addr_str); | 3669 | GNUNET_free (addr_str); |
3641 | /* Get address to bind to */ | 3670 | /* Get address to bind to */ |
3642 | if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_string(cfg, "gns-proxy", | 3671 | if (GNUNET_OK != GNUNET_CONFIGURATION_get_value_string (cfg, "gns-proxy", |
3643 | "BIND_TO6", | 3672 | "BIND_TO6", |
3644 | &addr_str)) | 3673 | &addr_str)) |
3645 | { | 3674 | { |
3646 | //No address specified | 3675 | // No address specified |
3647 | GNUNET_log(GNUNET_ERROR_TYPE_ERROR, | 3676 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, |
3648 | "Don't know what to bind6 to...\n"); | 3677 | "Don't know what to bind6 to...\n"); |
3649 | GNUNET_free(addr_str); | 3678 | GNUNET_free (addr_str); |
3650 | GNUNET_SCHEDULER_shutdown(); | 3679 | GNUNET_SCHEDULER_shutdown (); |
3651 | return; | 3680 | return; |
3652 | } | 3681 | } |
3653 | if (1 != inet_pton(AF_INET6, addr_str, &address6)) | 3682 | if (1 != inet_pton (AF_INET6, addr_str, &address6)) |
3654 | { | 3683 | { |
3655 | GNUNET_log(GNUNET_ERROR_TYPE_ERROR, | 3684 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, |
3656 | "Unable to parse IPv6 address %s\n", | 3685 | "Unable to parse IPv6 address %s\n", |
3657 | addr_str); | 3686 | addr_str); |
3658 | GNUNET_free(addr_str); | 3687 | GNUNET_free (addr_str); |
3659 | GNUNET_SCHEDULER_shutdown(); | 3688 | GNUNET_SCHEDULER_shutdown (); |
3660 | return; | 3689 | return; |
3661 | } | 3690 | } |
3662 | GNUNET_free(addr_str); | 3691 | GNUNET_free (addr_str); |
3663 | 3692 | ||
3664 | if (NULL == (curl_multi = curl_multi_init())) | 3693 | if (NULL == (curl_multi = curl_multi_init ())) |
3665 | { | 3694 | { |
3666 | GNUNET_log(GNUNET_ERROR_TYPE_ERROR, | 3695 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, |
3667 | "Failed to create cURL multi handle!\n"); | 3696 | "Failed to create cURL multi handle!\n"); |
3668 | return; | 3697 | return; |
3669 | } | 3698 | } |
3670 | cafile = cafile_opt; | 3699 | cafile = cafile_opt; |
3671 | if (NULL == cafile) | 3700 | if (NULL == cafile) |
3672 | { | 3701 | { |
3673 | if (GNUNET_OK != | 3702 | if (GNUNET_OK != |
3674 | GNUNET_CONFIGURATION_get_value_filename(cfg, | 3703 | GNUNET_CONFIGURATION_get_value_filename (cfg, |
3675 | "gns-proxy", | 3704 | "gns-proxy", |
3676 | "PROXY_CACERT", | 3705 | "PROXY_CACERT", |
3677 | &cafile_cfg)) | 3706 | &cafile_cfg)) |
3678 | { | 3707 | { |
3679 | GNUNET_log_config_missing(GNUNET_ERROR_TYPE_ERROR, | 3708 | GNUNET_log_config_missing (GNUNET_ERROR_TYPE_ERROR, |
3680 | "gns-proxy", | 3709 | "gns-proxy", |
3681 | "PROXY_CACERT"); | 3710 | "PROXY_CACERT"); |
3682 | return; | 3711 | return; |
3683 | } | ||
3684 | cafile = cafile_cfg; | ||
3685 | } | 3712 | } |
3686 | GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, | 3713 | cafile = cafile_cfg; |
3687 | "Using `%s' as CA\n", | 3714 | } |
3688 | cafile); | 3715 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
3716 | "Using `%s' as CA\n", | ||
3717 | cafile); | ||
3689 | 3718 | ||
3690 | gnutls_global_init(); | 3719 | gnutls_global_init (); |
3691 | gnutls_x509_crt_init(&proxy_ca.cert); | 3720 | gnutls_x509_crt_init (&proxy_ca.cert); |
3692 | gnutls_x509_privkey_init(&proxy_ca.key); | 3721 | gnutls_x509_privkey_init (&proxy_ca.key); |
3693 | 3722 | ||
3694 | if ((GNUNET_OK != | 3723 | if ((GNUNET_OK != |
3695 | load_cert_from_file(proxy_ca.cert, | 3724 | load_cert_from_file (proxy_ca.cert, |
3696 | cafile)) || | 3725 | cafile)) || |
3697 | (GNUNET_OK != | 3726 | (GNUNET_OK != |
3698 | load_key_from_file(proxy_ca.key, | 3727 | load_key_from_file (proxy_ca.key, |
3699 | cafile))) | 3728 | cafile))) |
3700 | { | 3729 | { |
3701 | GNUNET_log(GNUNET_ERROR_TYPE_ERROR, | 3730 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, |
3702 | _("Failed to load X.509 key and certificate from `%s'\n"), | 3731 | _ ("Failed to load X.509 key and certificate from `%s'\n"), |
3703 | cafile); | 3732 | cafile); |
3704 | gnutls_x509_crt_deinit(proxy_ca.cert); | 3733 | gnutls_x509_crt_deinit (proxy_ca.cert); |
3705 | gnutls_x509_privkey_deinit(proxy_ca.key); | 3734 | gnutls_x509_privkey_deinit (proxy_ca.key); |
3706 | gnutls_global_deinit(); | 3735 | gnutls_global_deinit (); |
3707 | GNUNET_free_non_null(cafile_cfg); | 3736 | GNUNET_free_non_null (cafile_cfg); |
3708 | return; | 3737 | return; |
3709 | } | 3738 | } |
3710 | GNUNET_free_non_null(cafile_cfg); | 3739 | GNUNET_free_non_null (cafile_cfg); |
3711 | if (NULL == (gns_handle = GNUNET_GNS_connect(cfg))) | 3740 | if (NULL == (gns_handle = GNUNET_GNS_connect (cfg))) |
3712 | { | 3741 | { |
3713 | GNUNET_log(GNUNET_ERROR_TYPE_ERROR, | 3742 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, |
3714 | "Unable to connect to GNS!\n"); | 3743 | "Unable to connect to GNS!\n"); |
3715 | gnutls_x509_crt_deinit(proxy_ca.cert); | 3744 | gnutls_x509_crt_deinit (proxy_ca.cert); |
3716 | gnutls_x509_privkey_deinit(proxy_ca.key); | 3745 | gnutls_x509_privkey_deinit (proxy_ca.key); |
3717 | gnutls_global_deinit(); | 3746 | gnutls_global_deinit (); |
3718 | return; | 3747 | return; |
3719 | } | 3748 | } |
3720 | GNUNET_SCHEDULER_add_shutdown(&do_shutdown, | 3749 | GNUNET_SCHEDULER_add_shutdown (&do_shutdown, |
3721 | NULL); | 3750 | NULL); |
3722 | 3751 | ||
3723 | /* Open listen socket for socks proxy */ | 3752 | /* Open listen socket for socks proxy */ |
3724 | lsock6 = bind_v6(); | 3753 | lsock6 = bind_v6 (); |
3725 | if (NULL == lsock6) | 3754 | if (NULL == lsock6) |
3755 | { | ||
3756 | GNUNET_log_strerror (GNUNET_ERROR_TYPE_ERROR, | ||
3757 | "bind"); | ||
3758 | } | ||
3759 | else | ||
3760 | { | ||
3761 | if (GNUNET_OK != | ||
3762 | GNUNET_NETWORK_socket_listen (lsock6, | ||
3763 | 5)) | ||
3726 | { | 3764 | { |
3727 | GNUNET_log_strerror(GNUNET_ERROR_TYPE_ERROR, | 3765 | GNUNET_log_strerror (GNUNET_ERROR_TYPE_ERROR, |
3728 | "bind"); | 3766 | "listen"); |
3767 | GNUNET_NETWORK_socket_close (lsock6); | ||
3768 | lsock6 = NULL; | ||
3729 | } | 3769 | } |
3730 | else | 3770 | else |
3731 | { | 3771 | { |
3732 | if (GNUNET_OK != | 3772 | ltask6 = GNUNET_SCHEDULER_add_read_net (GNUNET_TIME_UNIT_FOREVER_REL, |
3733 | GNUNET_NETWORK_socket_listen(lsock6, | 3773 | lsock6, |
3734 | 5)) | 3774 | &do_accept, |
3735 | { | 3775 | lsock6); |
3736 | GNUNET_log_strerror(GNUNET_ERROR_TYPE_ERROR, | ||
3737 | "listen"); | ||
3738 | GNUNET_NETWORK_socket_close(lsock6); | ||
3739 | lsock6 = NULL; | ||
3740 | } | ||
3741 | else | ||
3742 | { | ||
3743 | ltask6 = GNUNET_SCHEDULER_add_read_net(GNUNET_TIME_UNIT_FOREVER_REL, | ||
3744 | lsock6, | ||
3745 | &do_accept, | ||
3746 | lsock6); | ||
3747 | } | ||
3748 | } | 3776 | } |
3749 | lsock4 = bind_v4(); | 3777 | } |
3778 | lsock4 = bind_v4 (); | ||
3750 | if (NULL == lsock4) | 3779 | if (NULL == lsock4) |
3780 | { | ||
3781 | GNUNET_log_strerror (GNUNET_ERROR_TYPE_ERROR, | ||
3782 | "bind"); | ||
3783 | } | ||
3784 | else | ||
3785 | { | ||
3786 | if (GNUNET_OK != | ||
3787 | GNUNET_NETWORK_socket_listen (lsock4, | ||
3788 | 5)) | ||
3751 | { | 3789 | { |
3752 | GNUNET_log_strerror(GNUNET_ERROR_TYPE_ERROR, | 3790 | GNUNET_log_strerror (GNUNET_ERROR_TYPE_ERROR, |
3753 | "bind"); | 3791 | "listen"); |
3792 | GNUNET_NETWORK_socket_close (lsock4); | ||
3793 | lsock4 = NULL; | ||
3754 | } | 3794 | } |
3755 | else | 3795 | else |
3756 | { | 3796 | { |
3757 | if (GNUNET_OK != | 3797 | ltask4 = GNUNET_SCHEDULER_add_read_net (GNUNET_TIME_UNIT_FOREVER_REL, |
3758 | GNUNET_NETWORK_socket_listen(lsock4, | 3798 | lsock4, |
3759 | 5)) | 3799 | &do_accept, |
3760 | { | 3800 | lsock4); |
3761 | GNUNET_log_strerror(GNUNET_ERROR_TYPE_ERROR, | ||
3762 | "listen"); | ||
3763 | GNUNET_NETWORK_socket_close(lsock4); | ||
3764 | lsock4 = NULL; | ||
3765 | } | ||
3766 | else | ||
3767 | { | ||
3768 | ltask4 = GNUNET_SCHEDULER_add_read_net(GNUNET_TIME_UNIT_FOREVER_REL, | ||
3769 | lsock4, | ||
3770 | &do_accept, | ||
3771 | lsock4); | ||
3772 | } | ||
3773 | } | 3801 | } |
3802 | } | ||
3774 | if ((NULL == lsock4) && | 3803 | if ((NULL == lsock4) && |
3775 | (NULL == lsock6)) | 3804 | (NULL == lsock6)) |
3776 | { | 3805 | { |
3777 | GNUNET_SCHEDULER_shutdown(); | 3806 | GNUNET_SCHEDULER_shutdown (); |
3778 | return; | 3807 | return; |
3779 | } | 3808 | } |
3780 | if (0 != curl_global_init(CURL_GLOBAL_WIN32)) | 3809 | if (0 != curl_global_init (CURL_GLOBAL_WIN32)) |
3781 | { | 3810 | { |
3782 | GNUNET_log(GNUNET_ERROR_TYPE_ERROR, | 3811 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, |
3783 | "cURL global init failed!\n"); | 3812 | "cURL global init failed!\n"); |
3784 | GNUNET_SCHEDULER_shutdown(); | 3813 | GNUNET_SCHEDULER_shutdown (); |
3785 | return; | 3814 | return; |
3786 | } | 3815 | } |
3787 | GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, | 3816 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
3788 | "Proxy listens on port %u\n", | 3817 | "Proxy listens on port %u\n", |
3789 | (unsigned int)port); | 3818 | (unsigned int) port); |
3790 | 3819 | ||
3791 | /* start MHD daemon for HTTP */ | 3820 | /* start MHD daemon for HTTP */ |
3792 | hd = GNUNET_new(struct MhdHttpList); | 3821 | hd = GNUNET_new (struct MhdHttpList); |
3793 | hd->daemon = MHD_start_daemon(MHD_USE_DEBUG | MHD_USE_NO_LISTEN_SOCKET | MHD_ALLOW_SUSPEND_RESUME, | 3822 | hd->daemon = MHD_start_daemon (MHD_USE_DEBUG | MHD_USE_NO_LISTEN_SOCKET |
3794 | 0, | 3823 | | MHD_ALLOW_SUSPEND_RESUME, |
3795 | NULL, NULL, | 3824 | 0, |
3796 | &create_response, hd, | 3825 | NULL, NULL, |
3797 | MHD_OPTION_CONNECTION_TIMEOUT, (unsigned int)16, | 3826 | &create_response, hd, |
3798 | MHD_OPTION_NOTIFY_COMPLETED, &mhd_completed_cb, NULL, | 3827 | MHD_OPTION_CONNECTION_TIMEOUT, (unsigned |
3799 | MHD_OPTION_NOTIFY_CONNECTION, &mhd_connection_cb, NULL, | 3828 | int) 16, |
3800 | MHD_OPTION_URI_LOG_CALLBACK, &mhd_log_callback, NULL, | 3829 | MHD_OPTION_NOTIFY_COMPLETED, &mhd_completed_cb, |
3801 | MHD_OPTION_END); | 3830 | NULL, |
3831 | MHD_OPTION_NOTIFY_CONNECTION, | ||
3832 | &mhd_connection_cb, NULL, | ||
3833 | MHD_OPTION_URI_LOG_CALLBACK, &mhd_log_callback, | ||
3834 | NULL, | ||
3835 | MHD_OPTION_END); | ||
3802 | if (NULL == hd->daemon) | 3836 | if (NULL == hd->daemon) |
3803 | { | 3837 | { |
3804 | GNUNET_free(hd); | 3838 | GNUNET_free (hd); |
3805 | GNUNET_SCHEDULER_shutdown(); | 3839 | GNUNET_SCHEDULER_shutdown (); |
3806 | return; | 3840 | return; |
3807 | } | 3841 | } |
3808 | httpd = hd; | 3842 | httpd = hd; |
3809 | GNUNET_CONTAINER_DLL_insert(mhd_httpd_head, | 3843 | GNUNET_CONTAINER_DLL_insert (mhd_httpd_head, |
3810 | mhd_httpd_tail, | 3844 | mhd_httpd_tail, |
3811 | hd); | 3845 | hd); |
3812 | } | 3846 | } |
3813 | 3847 | ||
3814 | 3848 | ||
@@ -3820,53 +3854,54 @@ run(void *cls, | |||
3820 | * @return 0 ok, 1 on error | 3854 | * @return 0 ok, 1 on error |
3821 | */ | 3855 | */ |
3822 | int | 3856 | int |
3823 | main(int argc, | 3857 | main (int argc, |
3824 | char *const *argv) | 3858 | char *const *argv) |
3825 | { | 3859 | { |
3826 | struct GNUNET_GETOPT_CommandLineOption options[] = { | 3860 | struct GNUNET_GETOPT_CommandLineOption options[] = { |
3827 | GNUNET_GETOPT_option_uint16('p', | 3861 | GNUNET_GETOPT_option_uint16 ('p', |
3828 | "port", | 3862 | "port", |
3829 | NULL, | 3863 | NULL, |
3830 | gettext_noop("listen on specified port (default: 7777)"), | 3864 | gettext_noop ( |
3831 | &port), | 3865 | "listen on specified port (default: 7777)"), |
3832 | GNUNET_GETOPT_option_string('a', | 3866 | &port), |
3833 | "authority", | 3867 | GNUNET_GETOPT_option_string ('a', |
3834 | NULL, | 3868 | "authority", |
3835 | gettext_noop("pem file to use as CA"), | 3869 | NULL, |
3836 | &cafile_opt), | 3870 | gettext_noop ("pem file to use as CA"), |
3837 | GNUNET_GETOPT_option_flag('6', | 3871 | &cafile_opt), |
3838 | "disable-ivp6", | 3872 | GNUNET_GETOPT_option_flag ('6', |
3839 | gettext_noop("disable use of IPv6"), | 3873 | "disable-ivp6", |
3840 | &disable_v6), | 3874 | gettext_noop ("disable use of IPv6"), |
3875 | &disable_v6), | ||
3841 | 3876 | ||
3842 | GNUNET_GETOPT_OPTION_END | 3877 | GNUNET_GETOPT_OPTION_END |
3843 | }; | 3878 | }; |
3844 | static const char* page = | 3879 | static const char*page = |
3845 | "<html><head><title>gnunet-gns-proxy</title>" | 3880 | "<html><head><title>gnunet-gns-proxy</title>" |
3846 | "</head><body>cURL fail</body></html>"; | 3881 | "</head><body>cURL fail</body></html>"; |
3847 | int ret; | 3882 | int ret; |
3848 | 3883 | ||
3849 | if (GNUNET_OK != | 3884 | if (GNUNET_OK != |
3850 | GNUNET_STRINGS_get_utf8_args(argc, argv, | 3885 | GNUNET_STRINGS_get_utf8_args (argc, argv, |
3851 | &argc, &argv)) | 3886 | &argc, &argv)) |
3852 | return 2; | 3887 | return 2; |
3853 | GNUNET_log_setup("gnunet-gns-proxy", | 3888 | GNUNET_log_setup ("gnunet-gns-proxy", |
3854 | "WARNING", | 3889 | "WARNING", |
3855 | NULL); | 3890 | NULL); |
3856 | curl_failure_response | 3891 | curl_failure_response |
3857 | = MHD_create_response_from_buffer(strlen(page), | 3892 | = MHD_create_response_from_buffer (strlen (page), |
3858 | (void *)page, | 3893 | (void *) page, |
3859 | MHD_RESPMEM_PERSISTENT); | 3894 | MHD_RESPMEM_PERSISTENT); |
3860 | 3895 | ||
3861 | ret = | 3896 | ret = |
3862 | (GNUNET_OK == | 3897 | (GNUNET_OK == |
3863 | GNUNET_PROGRAM_run(argc, argv, | 3898 | GNUNET_PROGRAM_run (argc, argv, |
3864 | "gnunet-gns-proxy", | 3899 | "gnunet-gns-proxy", |
3865 | _("GNUnet GNS proxy"), | 3900 | _ ("GNUnet GNS proxy"), |
3866 | options, | 3901 | options, |
3867 | &run, NULL)) ? 0 : 1; | 3902 | &run, NULL)) ? 0 : 1; |
3868 | MHD_destroy_response(curl_failure_response); | 3903 | MHD_destroy_response (curl_failure_response); |
3869 | GNUNET_free_non_null((char *)argv); | 3904 | GNUNET_free_non_null ((char *) argv); |
3870 | return ret; | 3905 | return ret; |
3871 | } | 3906 | } |
3872 | 3907 | ||