GNUnet 0.28.1-dev.4-8-g14b9efcb0
 
Loading...
Searching...
No Matches
gnunet-daemon-hostlist_server.c File Reference

application to provide an integrated hostlist HTTP server More...

#include "platform.h"
#include "gnunet_common.h"
#include <microhttpd.h>
#include "gnunet-daemon-hostlist_server.h"
#include "gnunet_hello_uri_lib.h"
#include "gnunet_peerstore_service.h"
#include "gnunet-daemon-hostlist.h"
#include "gnunet_resolver_service.h"
#include "gnunet_mhd_compat.h"
#include <jansson.h>
#include <strings.h>
Include dependency graph for gnunet-daemon-hostlist_server.c:

Go to the source code of this file.

Data Structures

struct  HostSet
 Context for host_processor(). More...
 

Macros

#define GNUNET_ADV_TIMEOUT    GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MINUTES, 5)
 How long until our hostlist advertisement transmission via CORE should time out?
 

Functions

static void add_cors_headers (struct MHD_Response *resp)
 Add headers to a request indicating that we allow Cross-Origin Resource Sharing.
 
static struct MHD_Response * build_json_response (const struct HostSet *host_set)
 
static void finish_response ()
 Function that assembles our response.
 
static enum GNUNET_GenericReturnValue host_processor (void *cls, const struct GNUNET_PeerIdentity *peer, void *value)
 Callback that processes each of the known HELLOs for the hostlist response construction.
 
static MHD_RESULT accept_policy_callback (void *cls, const struct sockaddr *addr, socklen_t addrlen)
 Hostlist access policy (very permissive, allows everything).
 
static int header_iterator (void *cls, enum MHD_ValueKind kind, const char *key, const char *value)
 
static MHD_RESULT access_handler_callback (void *cls, struct MHD_Connection *connection, const char *url, const char *method, const char *version, const char *upload_data, size_t *upload_data_size, void **con_cls)
 Main request handler.
 
static void adv_transmit (struct GNUNET_MQ_Handle *mq)
 Handler called by CORE when CORE is ready to transmit message.
 
static void * connect_handler (void *cls, const struct GNUNET_PeerIdentity *peer, struct GNUNET_MQ_Handle *mq, enum GNUNET_CORE_PeerClass class)
 Method called whenever a given peer connects.
 
static void process_notify (void *cls, const struct GNUNET_PEERSTORE_Record *record, const char *err_msg)
 PEERSTORE calls this function to let us know about a possible peer that we might want to connect to.
 
static struct GNUNET_SCHEDULER_Taskprepare_daemon (struct MHD_Daemon *daemon_handle)
 Function that queries MHD's select sets and starts the task waiting for them.
 
static void run_daemon (void *cls)
 Call MHD to process pending requests and then go back and schedule the next run.
 
static void error_cb (void *cls)
 
static void sync_cb (void *cls)
 
static void start_notify (void *cls)
 
int GNUNET_HOSTLIST_server_start (const struct GNUNET_CONFIGURATION_Handle *c, struct GNUNET_STATISTICS_Handle *st, struct GNUNET_CORE_Handle *co, GNUNET_CORE_ConnectEventHandler *server_ch, int advertise)
 Start server offering our hostlist.
 
void GNUNET_HOSTLIST_server_stop ()
 Stop server offering our hostlist.
 

Variables

struct GNUNET_CONTAINER_MultiPeerMaphellos
 Map with hellos we build the hostlist with.
 
static struct MHD_Daemon * daemon_handle_v6
 Handle to the HTTP server as provided by libmicrohttpd for IPv6.
 
static struct MHD_Daemon * daemon_handle_v4
 Handle to the HTTP server as provided by libmicrohttpd for IPv4.
 
static const struct GNUNET_CONFIGURATION_Handlecfg
 Our configuration.
 
static struct GNUNET_STATISTICS_Handlestats
 For keeping statistics.
 
static struct GNUNET_CORE_Handlecore
 Handle to the core service (NULL until we've connected to it).
 
struct GNUNET_SCHEDULER_Taskpeerstore_notify_task
 The task to delayed start the notification process initially.
 
static struct GNUNET_PEERSTORE_Monitorpeerstore_notify
 Our peerstore notification context.
 
static struct GNUNET_SCHEDULER_Taskhostlist_task_v4
 Our primary task for IPv4.
 
static struct GNUNET_SCHEDULER_Taskhostlist_task_v6
 Our primary task for IPv6.
 
static struct MHD_Response * response
 Our canonical response.
 
static struct MHD_Response * response_json
 Our json response.
 
static struct GNUNET_PEERSTORE_Handlepeerstore
 Handle to the PEERSTORE service.
 
static int advertising
 Set if we are allowed to advertise our hostlist to others.
 
static char * hostlist_uri
 Buffer for the hostlist address.
 
static struct HostSetbuilder
 NULL if we are not currently iterating over peer information.
 

Detailed Description

application to provide an integrated hostlist HTTP server

Author
Christian Grothoff
Matthias Wachs
David Barksdale

Definition in file gnunet-daemon-hostlist_server.c.

Macro Definition Documentation

◆ GNUNET_ADV_TIMEOUT

#define GNUNET_ADV_TIMEOUT    GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_MINUTES, 5)

How long until our hostlist advertisement transmission via CORE should time out?

Definition at line 44 of file gnunet-daemon-hostlist_server.c.

128{
132 char *data;
133
137 unsigned int size;
138};
139
140
144static struct HostSet *builder;
145
146
153static void
154add_cors_headers (struct MHD_Response *resp)
155{
156 GNUNET_assert (MHD_NO !=
157 MHD_add_response_header (resp,
158 "Access-Control-Allow-Origin", "*"));
159 GNUNET_assert (MHD_NO !=
160 MHD_add_response_header (resp,
161 "Access-Control-Allow-Methods",
162 "GET, OPTIONS"));
163 GNUNET_assert (MHD_NO !=
164 MHD_add_response_header (resp, "Access-Control-Max-Age",
165 "86400"));
166}
167
168
169static struct MHD_Response*
170build_json_response (const struct HostSet *host_set)
171{
172 struct GNUNET_MessageHeader *hello;
173 struct GNUNET_HELLO_Parser *hparser;
174 json_t*hello_uri_j;
175 json_t*hello_array;
176 char *hello_uri;
177 char *hello_uris;
178 size_t offset = 0;
179
180 hello_uri_j = json_object ();
181 hello_array = json_array ();
182 while (offset < host_set->size)
183 {
184 hello = (struct GNUNET_MessageHeader*) (host_set->data + offset);
185 hparser = GNUNET_HELLO_parser_from_msg (hello, NULL);
186 if (NULL == hparser)
187 {
189 "HELLO from host set malformed, skipping...\n");
190 offset += ntohs (hello->size);
191 continue;
192 }
193 hello_uri = GNUNET_HELLO_parser_to_url (hparser);
194 json_array_append_new (hello_array, json_string (hello_uri));
195 GNUNET_free (hello_uri);
196 GNUNET_HELLO_parser_free (hparser);
197 offset += ntohs (hello->size);
198 }
199 json_object_set_new (hello_uri_j, "hellos", hello_array);
200 hello_uris = json_dumps (hello_uri_j, JSON_INDENT (2));
201 json_decref (hello_uri_j);
202 return MHD_create_response_from_buffer (strlen (hello_uris),
203 hello_uris,
204 MHD_RESPMEM_MUST_FREE);
205}
206
207
211static void
213{
214 if (NULL != response)
215 MHD_destroy_response (response);
216 if (NULL != response_json)
217 MHD_destroy_response (response_json);
219 "Creating hostlist response with %u bytes\n",
220 (unsigned int) builder->size);
221 response = MHD_create_response_from_buffer (builder->size,
222 builder->data,
223 MHD_RESPMEM_MUST_FREE);
225 GNUNET_assert (MHD_NO != MHD_add_response_header (response_json,
226 "Content-Type",
227 "application/json"));
229 if ((NULL == daemon_handle_v4) && (NULL == daemon_handle_v6))
230 {
231 MHD_destroy_response (response);
232 response = NULL;
233 MHD_destroy_response (response_json);
234 response_json = NULL;
235 }
237 gettext_noop ("bytes in hostlist"),
238 builder->size,
239 GNUNET_YES);
241 builder = NULL;
242}
243
244
255host_processor (void *cls,
256 const struct GNUNET_PeerIdentity *peer,
257 void *value)
258{
259 size_t old;
260 size_t s;
261 struct GNUNET_MessageHeader *hello = value;
262 (void) cls;
263
265 "host_processor\n");
266 old = builder->size;
267 s = ntohs (hello->size);
269 "Received %u bytes of `%s' from peer `%s' for hostlist.\n",
270 (unsigned int) s,
271 "HELLO",
272 GNUNET_i2s (peer));
273 if ((old + s >= GNUNET_MAX_MALLOC_CHECKED) ||
274 (old + s >= MAX_BYTES_PER_HOSTLISTS))
275 {
276 /* too large, skip! */
279 "bytes not included in hostlist (size limit)"),
280 s,
281 GNUNET_NO);
282 return GNUNET_YES;
283 }
285 "Adding peer `%s' to hostlist (%u bytes)\n",
286 GNUNET_i2s (peer),
287 (unsigned int) s);
289 GNUNET_memcpy (&builder->data[old], hello, s);
290
291 return GNUNET_YES;
292}
293
294
304static MHD_RESULT
305accept_policy_callback (void *cls,
306 const struct sockaddr *addr,
307 socklen_t addrlen)
308{
309 if (NULL == response)
310 {
311 GNUNET_log (
313 "Received request for hostlist, but I am not yet ready; rejecting!\n");
314 return MHD_NO;
315 }
316 return MHD_YES; /* accept all */
317}
318
319
320static int
321header_iterator (void *cls,
322 enum MHD_ValueKind kind,
323 const char *key,
324 const char *value)
325{
326 enum GNUNET_GenericReturnValue *want_json = cls;
327
328 if (0 != strcasecmp (key, "Accept"))
329 return GNUNET_YES;
330 if (0 == strcasecmp (value, "application/json"))
331 *want_json = GNUNET_YES;
332 return MHD_YES;
333}
334
335
371static MHD_RESULT
372access_handler_callback (void *cls,
373 struct MHD_Connection *connection,
374 const char *url,
375 const char *method,
376 const char *version,
377 const char *upload_data,
378 size_t *upload_data_size,
379 void **con_cls)
380{
381 static int dummy;
382 struct MHD_Response *selected_response;
383 enum GNUNET_GenericReturnValue want_json = GNUNET_NO;
384
385 /* CORS pre-flight request */
386 if (0 == strcmp (MHD_HTTP_METHOD_OPTIONS, method))
387 {
388 struct MHD_Response *options_response;
389 int rc;
390
391 options_response =
392 MHD_create_response_from_buffer (0, NULL, MHD_RESPMEM_PERSISTENT);
393 add_cors_headers (options_response);
394 rc = MHD_queue_response (connection, MHD_HTTP_OK, options_response);
395 MHD_destroy_response (options_response);
396 return rc;
397 }
398 if (0 != strcmp (method, MHD_HTTP_METHOD_GET))
399 {
401 _ ("Refusing `%s' request to hostlist server\n"),
402 method);
405 "hostlist requests refused (not HTTP GET)"),
406 1,
407 GNUNET_YES);
408 return MHD_NO;
409 }
410 if (NULL == *con_cls)
411 {
412 (*con_cls) = &dummy;
413 return MHD_YES;
414 }
415 if (0 != *upload_data_size)
416 {
418 _ ("Refusing `%s' request with %llu bytes of upload data\n"),
419 method,
420 (unsigned long long) *upload_data_size);
423 "hostlist requests refused (upload data)"),
424 1,
425 GNUNET_YES);
426 return MHD_NO; /* do not support upload data */
427 }
428 selected_response = response;
429 MHD_get_connection_values (connection,
430 MHD_HEADER_KIND,
431 (MHD_KeyValueIterator) & header_iterator,
432 &want_json);
433 if (GNUNET_YES == want_json)
434 {
435 selected_response = response_json;
436 }
437 if (NULL == selected_response)
438 {
439 GNUNET_log (
441 _ (
442 "Could not handle hostlist request since I do not have a response yet\n"));
445 "hostlist requests refused (not ready)"),
446 1,
447 GNUNET_YES);
448 return MHD_NO; /* internal error, no response yet */
449 }
451 _ ("Received request for our hostlist\n"));
453 gettext_noop ("hostlist requests processed"),
454 1,
455 GNUNET_YES);
456 return MHD_queue_response (connection, MHD_HTTP_OK, selected_response);
457}
458
459
469static void
471{
472 static uint64_t hostlist_adv_count;
473 size_t uri_size; /* Including \0 termination! */
474 struct GNUNET_MessageHeader *header;
475 struct GNUNET_MQ_Envelope *env;
476
477 uri_size = strlen (hostlist_uri) + 1;
478 env = GNUNET_MQ_msg_extra (header,
479 uri_size,
481 GNUNET_memcpy (&header[1], hostlist_uri, uri_size);
487 "Sent advertisement message: Copied %u bytes into buffer!\n",
488 (unsigned int) uri_size);
489 hostlist_adv_count++;
491 " # Sent advertisement message: %llu\n",
492 (unsigned long long) hostlist_adv_count);
494 gettext_noop ("# hostlist advertisements send"),
495 1,
496 GNUNET_NO);
497}
498
499
509static void *
510connect_handler (void *cls,
511 const struct GNUNET_PeerIdentity *peer,
512 struct GNUNET_MQ_Handle *mq,
513 enum GNUNET_CORE_PeerClass class)
514{
515 size_t size;
516
517 if (! advertising)
518 return NULL;
519 if (NULL == hostlist_uri)
520 return NULL;
521 size = strlen (hostlist_uri) + 1;
522 if (size + sizeof(struct GNUNET_MessageHeader) >= GNUNET_MAX_MESSAGE_SIZE)
523 {
524 GNUNET_break (0);
525 return NULL;
526 }
527 size += sizeof(struct GNUNET_MessageHeader);
528 if (NULL == core)
529 {
530 GNUNET_break (0);
531 return NULL;
532 }
533 GNUNET_log (
535 "Asked CORE to transmit advertisement message with a size of %u bytes to peer `%s'\n",
536 (unsigned int) size,
537 GNUNET_i2s (peer));
539 return NULL;
540}
541
542
552static void
553process_notify (void *cls,
554 const struct GNUNET_PEERSTORE_Record *record,
555 const char *err_msg)
556{
557 unsigned int map_size;
558 struct GNUNET_MessageHeader *hello_cpy;
559 struct GNUNET_PeerIdentity *peer_cpy;
560 struct GNUNET_MessageHeader *hello;
561
564 "Peerstore is notifying us to rebuild our hostlist map size %u\n",
565 map_size);
566 if (NULL != err_msg)
567 {
569 _ ("Error in communication with PEERSTORE service: %s\n"),
570 err_msg);
572 return;
573 }
574 if (NULL == record)
575 {
576 GNUNET_break (0);
578 return;
579 }
580 hello = record->value;
581 /* @e value and @e value_size are independent, and the HELLO is an
582 unvalidated blob a remote peer published: a zero-length value leaves
583 @a hello NULL, and a @e size field larger than @e value_size makes the
584 GNUNET_memcpy() below read past the end of the record. */
585 if ((NULL == hello) ||
586 (record->value_size < sizeof (*hello)) ||
587 (ntohs (hello->size) > record->value_size))
588 {
589 GNUNET_break_op (0);
591 return;
592 }
593 if (NULL != builder)
594 {
596 builder->size = 0;
597 builder->data = NULL;
598 }
599 else
600 {
601 builder = GNUNET_new (struct HostSet);
602 }
603
604 peer_cpy = GNUNET_malloc (sizeof (struct GNUNET_PeerIdentity));
605 GNUNET_memcpy (peer_cpy, &record->peer, sizeof (struct GNUNET_PeerIdentity));
606 hello_cpy = GNUNET_malloc (ntohs (hello->size));
607 GNUNET_memcpy (hello_cpy, hello, ntohs (hello->size));
610 peer_cpy,
611 (struct
613 hello_cpy,
617 NULL))
621 "1 Peerstore is notifying us to rebuild our hostlist map size %u peer %s\n",
622 map_size,
623 GNUNET_i2s (&record->peer));
625}
626
627
632static struct GNUNET_SCHEDULER_Task *
633prepare_daemon (struct MHD_Daemon *daemon_handle);
634
635
642static void
643run_daemon (void *cls)
644{
645 struct MHD_Daemon *daemon_handle = cls;
646
647 if (daemon_handle == daemon_handle_v4)
648 hostlist_task_v4 = NULL;
649 else
650 hostlist_task_v6 = NULL;
651 GNUNET_assert (MHD_YES == MHD_run (daemon_handle));
652 if (daemon_handle == daemon_handle_v4)
653 hostlist_task_v4 = prepare_daemon (daemon_handle);
654 else
655 hostlist_task_v6 = prepare_daemon (daemon_handle);
656}
657
658
665static struct GNUNET_SCHEDULER_Task *
666prepare_daemon (struct MHD_Daemon *daemon_handle)
667{
669 fd_set rs;
670 fd_set ws;
671 fd_set es;
672 struct GNUNET_NETWORK_FDSet *wrs;
673 struct GNUNET_NETWORK_FDSet *wws;
674 int max;
675 MHD_UNSIGNED_LONG_LONG timeout;
676 int haveto;
677 struct GNUNET_TIME_Relative tv;
678
679 FD_ZERO (&rs);
680 FD_ZERO (&ws);
681 FD_ZERO (&es);
684 max = -1;
685 GNUNET_assert (MHD_YES == MHD_get_fdset (daemon_handle, &rs, &ws, &es, &max));
686 haveto = MHD_get_timeout (daemon_handle, &timeout);
687 if (haveto == MHD_YES)
688 tv.rel_value_us = (uint64_t) timeout * 1000LL;
689 else
694 tv,
695 wrs,
696 wws,
697 &run_daemon,
698 daemon_handle);
701 return ret;
702}
703
704
705static void
706error_cb (void *cls)
707{
709 "Error in PEERSTORE monitoring\n");
710}
711
712
713static void
714sync_cb (void *cls)
715{
717 "Done with initial PEERSTORE iteration during monitoring\n");
718}
719
720
721static void
722start_notify (void *cls)
723{
724 (void) cls;
725
727 "Starting to process new hellos to add to hostlist.\n");
730 "peerstore",
731 NULL,
733 &error_cb,
734 NULL,
735 &sync_cb,
736 NULL,
737 &process_notify, NULL);
738}
739
740
751int
754 struct GNUNET_CORE_Handle *co,
756 int advertise)
757{
758 unsigned long long port;
759 char *hostname;
760 char *ipv4;
761 char *ipv6;
762 size_t size;
763 struct in_addr i4;
764 struct in6_addr i6;
765 struct sockaddr_in v4;
766 struct sockaddr_in6 v6;
767 const struct sockaddr *sa4;
768 const struct sockaddr *sa6;
769
771 advertising = advertise;
772 if (! advertising)
773 {
775 "Advertising not enabled on this hostlist server\n");
776 }
777 else
778 {
780 "Advertising enabled on this hostlist server\n");
781 }
782 cfg = c;
783 stats = st;
785 if (NULL == peerstore)
786 {
788 _ ("Could not access PEERSTORE service. Exiting.\n"));
789 return GNUNET_SYSERR;
790 }
792 "HOSTLIST",
793 "HTTPPORT",
794 &port))
795 return GNUNET_SYSERR;
796 if ((0 == port) || (port > UINT16_MAX))
797 {
799 _ ("Invalid port number %llu. Exiting.\n"),
800 port);
801 return GNUNET_SYSERR;
802 }
803
804 if (GNUNET_SYSERR ==
806 "HOSTLIST",
807 "EXTERNAL_DNS_NAME",
808 &hostname))
809 hostname = GNUNET_RESOLVER_local_fqdn_get ();
811 _ ("Hostlist service starts on %s:%llu\n"),
812 hostname,
813 port);
814 if (NULL != hostname)
815 {
816 size = strlen (hostname);
817 if (size + 15 > MAX_URL_LEN)
818 {
819 GNUNET_break (0);
820 }
821 else
822 {
824 "http://%s:%u/",
825 hostname,
826 (unsigned int) port);
828 _ ("Address to obtain hostlist: `%s'\n"),
830 }
831 GNUNET_free (hostname);
832 }
833
834 if (GNUNET_CONFIGURATION_have_value (cfg, "HOSTLIST", "BINDTOIPV4"))
835 {
837 "HOSTLIST",
838 "BINDTOIP",
839 &ipv4))
840 {
841 GNUNET_log (
843 _ ("BINDTOIP does not a valid IPv4 address! Ignoring BINDTOIPV4.\n"));
844 }
845 }
846 else
847 ipv4 = NULL;
848 if (GNUNET_CONFIGURATION_have_value (cfg, "HOSTLIST", "BINDTOIPV6"))
849 {
851 "HOSTLIST",
852 "BINDTOIP",
853 &ipv6))
854 {
855 GNUNET_log (
857 _ ("BINDTOIP does not a valid IPv4 address! Ignoring BINDTOIPV6.\n"));
858 }
859 }
860 else
861 ipv6 = NULL;
862 sa4 = NULL;
863 if (NULL != ipv4)
864 {
865 if (1 == inet_pton (AF_INET, ipv4, &i4))
866 {
867 memset (&v4, 0, sizeof(v4));
868 v4.sin_family = AF_INET;
869 v4.sin_addr = i4;
870 v4.sin_port = htons (port);
871#if HAVE_SOCKADDR_IN_SIN_LEN
872 v4.sin_len = sizeof(v4);
873#endif
874 sa4 = (const struct sockaddr *) &v4;
875 }
876 else
878 _ (
879 "`%s' is not a valid IPv4 address! Ignoring BINDTOIPV4.\n"),
880 ipv4);
882 }
883 sa6 = NULL;
884 if (NULL != ipv6)
885 {
886 if (1 == inet_pton (AF_INET6, ipv6, &i6))
887 {
888 memset (&v6, 0, sizeof(v6));
889 v6.sin6_family = AF_INET6;
890 v6.sin6_addr = i6;
891 v6.sin6_port = htons (port);
892#if HAVE_SOCKADDR_IN_SIN_LEN
893 v6.sin6_len = sizeof(v6);
894#endif
895 sa6 = (const struct sockaddr *) &v6;
896 }
897 else
899 _ (
900 "`%s' is not a valid IPv6 address! Ignoring BINDTOIPV6.\n"),
901 ipv6);
903 }
904
905 daemon_handle_v6 = MHD_start_daemon (MHD_USE_IPv6 | MHD_USE_DEBUG,
906 (uint16_t) port,
908 NULL,
910 NULL,
911 MHD_OPTION_CONNECTION_LIMIT,
912 (unsigned int) 128,
913 MHD_OPTION_PER_IP_CONNECTION_LIMIT,
914 (unsigned int) 32,
915 MHD_OPTION_CONNECTION_TIMEOUT,
916 (unsigned int) 16,
917 MHD_OPTION_CONNECTION_MEMORY_LIMIT,
918 (size_t) (16 * 1024),
919 MHD_OPTION_SOCK_ADDR,
920 sa6,
921 MHD_OPTION_END);
922 daemon_handle_v4 = MHD_start_daemon (MHD_NO_FLAG | MHD_USE_DEBUG,
923 (uint16_t) port,
925 NULL,
927 NULL,
928 MHD_OPTION_CONNECTION_LIMIT,
929 (unsigned int) 128,
930 MHD_OPTION_PER_IP_CONNECTION_LIMIT,
931 (unsigned int) 32,
932 MHD_OPTION_CONNECTION_TIMEOUT,
933 (unsigned int) 16,
934 MHD_OPTION_CONNECTION_MEMORY_LIMIT,
935 (size_t) (16 * 1024),
936 MHD_OPTION_SOCK_ADDR,
937 sa4,
938 MHD_OPTION_END);
939
940 if ((NULL == daemon_handle_v6) && (NULL == daemon_handle_v4))
941 {
943 _ ("Could not start hostlist HTTP server on port %u\n"),
944 (unsigned short) port);
945 return GNUNET_SYSERR;
946 }
947
948 core = co;
950 if (NULL != daemon_handle_v4)
952 if (NULL != daemon_handle_v6)
957 NULL);
958 return GNUNET_OK;
959}
960
961
965void
967{
968 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Hostlist server shutdown\n");
969 if (NULL != hostlist_task_v6)
970 {
972 hostlist_task_v6 = NULL;
973 }
974 if (NULL != hostlist_task_v4)
975 {
977 hostlist_task_v4 = NULL;
978 }
979 if (NULL != daemon_handle_v4)
980 {
981 MHD_stop_daemon (daemon_handle_v4);
982 daemon_handle_v4 = NULL;
983 }
984 if (NULL != daemon_handle_v6)
985 {
986 MHD_stop_daemon (daemon_handle_v6);
987 daemon_handle_v6 = NULL;
988 }
989 if (NULL != response)
990 {
991 MHD_destroy_response (response);
992 response = NULL;
993 }
994 if (NULL != response_json)
995 {
996 MHD_destroy_response (response_json);
997 response_json = NULL;
998 }
999 if (NULL != peerstore_notify)
1000 {
1002 peerstore_notify = NULL;
1003 }
1004 else if (NULL != peerstore_notify_task)
1005 {
1007 }
1008 if (NULL != builder)
1009 {
1012 builder = NULL;
1013 }
1014 if (NULL != peerstore)
1015 {
1017 peerstore = NULL;
1018 }
1019 cfg = NULL;
1020 stats = NULL;
1021 core = NULL;
1022}
1023
1024
1025/* end of gnunet-daemon-hostlist_server.c */
struct GNUNET_MQ_Envelope * env
Definition 005.c:1
#define gettext_noop(String)
Definition gettext.h:74
static int ret
Final status code.
Definition gnunet-arm.c:93
static struct GNUNET_TIME_Relative timeout
User defined timestamp for completing operations.
Definition gnunet-arm.c:118
static uint16_t port
Port number.
Definition gnunet-bcd.c:146
static struct GNUNET_SCHEDULER_Task * st
The shutdown task.
static void record(void *cls, size_t data_size, const void *data)
Process recorded audio data.
static GNUNET_CORE_ConnectEventHandler server_ch
Handle to hostlist server's connect handler.
#define MAX_URL_LEN
How long can hostlist URLs be?
#define MAX_BYTES_PER_HOSTLISTS
How many bytes do we download at most from a hostlist server?
static struct MHD_Daemon * daemon_handle_v6
Handle to the HTTP server as provided by libmicrohttpd for IPv6.
static struct MHD_Response * response
Our canonical response.
static void * connect_handler(void *cls, const struct GNUNET_PeerIdentity *peer, struct GNUNET_MQ_Handle *mq, enum GNUNET_CORE_PeerClass class)
Method called whenever a given peer connects.
static void sync_cb(void *cls)
static struct MHD_Daemon * daemon_handle_v4
Handle to the HTTP server as provided by libmicrohttpd for IPv4.
static struct GNUNET_SCHEDULER_Task * hostlist_task_v4
Our primary task for IPv4.
static struct HostSet * builder
NULL if we are not currently iterating over peer information.
static struct GNUNET_CORE_Handle * core
Handle to the core service (NULL until we've connected to it).
static int advertising
Set if we are allowed to advertise our hostlist to others.
static struct MHD_Response * build_json_response(const struct HostSet *host_set)
static void add_cors_headers(struct MHD_Response *resp)
Add headers to a request indicating that we allow Cross-Origin Resource Sharing.
static struct GNUNET_PEERSTORE_Monitor * peerstore_notify
Our peerstore notification context.
static struct GNUNET_STATISTICS_Handle * stats
For keeping statistics.
struct GNUNET_CONTAINER_MultiPeerMap * hellos
Map with hellos we build the hostlist with.
static const struct GNUNET_CONFIGURATION_Handle * cfg
Our configuration.
static struct GNUNET_SCHEDULER_Task * hostlist_task_v6
Our primary task for IPv6.
static struct GNUNET_PEERSTORE_Handle * peerstore
Handle to the PEERSTORE service.
static enum GNUNET_GenericReturnValue host_processor(void *cls, const struct GNUNET_PeerIdentity *peer, void *value)
Callback that processes each of the known HELLOs for the hostlist response construction.
static struct GNUNET_SCHEDULER_Task * prepare_daemon(struct MHD_Daemon *daemon_handle)
Function that queries MHD's select sets and starts the task waiting for them.
static void start_notify(void *cls)
static struct MHD_Response * response_json
Our json response.
static void adv_transmit(struct GNUNET_MQ_Handle *mq)
Handler called by CORE when CORE is ready to transmit message.
struct GNUNET_SCHEDULER_Task * peerstore_notify_task
The task to delayed start the notification process initially.
int GNUNET_HOSTLIST_server_start(const struct GNUNET_CONFIGURATION_Handle *c, struct GNUNET_STATISTICS_Handle *st, struct GNUNET_CORE_Handle *co, GNUNET_CORE_ConnectEventHandler *server_ch, int advertise)
Start server offering our hostlist.
static void run_daemon(void *cls)
Call MHD to process pending requests and then go back and schedule the next run.
static int header_iterator(void *cls, enum MHD_ValueKind kind, const char *key, const char *value)
static void finish_response()
Function that assembles our response.
static void error_cb(void *cls)
static MHD_RESULT access_handler_callback(void *cls, struct MHD_Connection *connection, const char *url, const char *method, const char *version, const char *upload_data, size_t *upload_data_size, void **con_cls)
Main request handler.
static void process_notify(void *cls, const struct GNUNET_PEERSTORE_Record *record, const char *err_msg)
PEERSTORE calls this function to let us know about a possible peer that we might want to connect to.
void GNUNET_HOSTLIST_server_stop()
Stop server offering our hostlist.
static char * hostlist_uri
Buffer for the hostlist address.
static MHD_RESULT accept_policy_callback(void *cls, const struct sockaddr *addr, socklen_t addrlen)
Hostlist access policy (very permissive, allows everything).
static char * data
The data to insert into the dht.
struct GNUNET_HashCode key
The key used in the DHT.
static struct in_addr dummy
Target "dummy" address of the packet we pretend to respond to.
static char * value
Value of the record to add/remove.
static int ipv4
Option -4: IPv4 requested.
Definition gnunet-vpn.c:60
static int ipv6
Option -6: IPv6 requested.
Definition gnunet-vpn.c:65
static unsigned int map_size
Command-line argument specifying desired size of the hash map with all of our pending names.
#define MHD_RESULT
Data type to use for functions return an "MHD result".
#define GNUNET_MAX_MESSAGE_SIZE
Largest supported message (to be precise, one byte more than the largest possible message,...
enum GNUNET_GenericReturnValue GNUNET_CONFIGURATION_get_value_number(const struct GNUNET_CONFIGURATION_Handle *cfg, const char *section, const char *option, unsigned long long *number)
Get a configuration value that should be a number.
enum GNUNET_GenericReturnValue GNUNET_CONFIGURATION_get_value_string(const struct GNUNET_CONFIGURATION_Handle *cfg, const char *section, const char *option, char **value)
Get a configuration value that should be a string.
enum GNUNET_GenericReturnValue GNUNET_CONFIGURATION_have_value(const struct GNUNET_CONFIGURATION_Handle *cfg, const char *section, const char *option)
Test if we have a value for a particular option.
GNUNET_CORE_PeerClass
The peer class gives a hint about the capabilities of a peer.
void *(* GNUNET_CORE_ConnectEventHandler)(void *cls, const struct GNUNET_PeerIdentity *peer, struct GNUNET_MQ_Handle *mq, enum GNUNET_CORE_PeerClass class)
Method called whenever a given peer connects.
int GNUNET_CONTAINER_multipeermap_iterate(struct GNUNET_CONTAINER_MultiPeerMap *map, GNUNET_CONTAINER_PeerMapIterator it, void *it_cls)
Iterate over all entries in the map.
struct GNUNET_CONTAINER_MultiPeerMap * GNUNET_CONTAINER_multipeermap_create(unsigned int len, int do_not_copy_keys)
Create a multi peer map (hash map for public keys of peers).
unsigned int GNUNET_CONTAINER_multipeermap_size(const struct GNUNET_CONTAINER_MultiPeerMap *map)
Get the number of key-value pairs in the map.
int GNUNET_CONTAINER_multipeermap_put(struct GNUNET_CONTAINER_MultiPeerMap *map, const struct GNUNET_PeerIdentity *key, void *value, enum GNUNET_CONTAINER_MultiHashMapOption opt)
Store a key-value pair in the map.
@ GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE
Allow multiple values with the same key.
void GNUNET_HELLO_parser_free(struct GNUNET_HELLO_Parser *parser)
Release resources of a builder.
Definition hello-uri.c:380
char * GNUNET_HELLO_parser_to_url(const struct GNUNET_HELLO_Parser *parser)
Generate GNUnet HELLO URI from a parser.
Definition hello-uri.c:867
struct GNUNET_HELLO_Parser * GNUNET_HELLO_parser_from_msg(const struct GNUNET_MessageHeader *msg, const struct GNUNET_PeerIdentity *pid)
Parse msg.
Definition hello-uri.c:416
#define GNUNET_log(kind,...)
#define GNUNET_memcpy(dst, src, n)
Call memcpy() but check for n being 0 first.
GNUNET_GenericReturnValue
Named constants for return values.
uint16_t size
The length of the struct (in bytes, including the length field itself), in big-endian format.
@ GNUNET_SCHEDULER_PRIORITY_HIGH
Run with high priority (important requests).
@ GNUNET_OK
@ GNUNET_YES
@ GNUNET_NO
@ GNUNET_SYSERR
#define GNUNET_break_op(cond)
Use this for assertion violations caused by other peers (i.e.
const char * GNUNET_i2s(const struct GNUNET_PeerIdentity *pid)
Convert a peer identity to a string (for printing debug messages).
#define GNUNET_assert(cond)
Use this for fatal errors that cannot be handled.
#define GNUNET_break(cond)
Use this for internal assertion violations that are not fatal (can be handled) but should not occur.
@ GNUNET_ERROR_TYPE_WARNING
@ GNUNET_ERROR_TYPE_ERROR
@ GNUNET_ERROR_TYPE_DEBUG
@ GNUNET_ERROR_TYPE_INFO
int int GNUNET_asprintf(char **buf, const char *format,...) __attribute__((format(printf
Like asprintf, just portable.
#define GNUNET_MAX_MALLOC_CHECKED
Maximum allocation with GNUNET_malloc macro.
#define GNUNET_array_grow(arr, size, tsize)
Grow a well-typed (!) array.
#define GNUNET_new(type)
Allocate a struct or union of the given type.
#define GNUNET_malloc(size)
Wrapper around malloc.
#define GNUNET_free(ptr)
Wrapper around free.
void GNUNET_MQ_env_set_options(struct GNUNET_MQ_Envelope *env, enum GNUNET_MQ_PriorityPreferences pp)
Set application-specific options for this envelope.
Definition mq.c:879
void GNUNET_MQ_send(struct GNUNET_MQ_Handle *mq, struct GNUNET_MQ_Envelope *ev)
Send a message with the given message queue.
Definition mq.c:337
#define GNUNET_MQ_msg_extra(mvar, esize, type)
Allocate an envelope, with extra space allocated after the space needed by the message struct.
@ GNUNET_MQ_PREF_CORK_ALLOWED
Flag to indicate that CORKing is acceptable.
@ GNUNET_MQ_PREF_UNRELIABLE
Flag to indicate that unreliable delivery is acceptable.
void GNUNET_NETWORK_fdset_destroy(struct GNUNET_NETWORK_FDSet *fds)
Releases the associated memory of an fd set.
Definition network.c:1184
void GNUNET_NETWORK_fdset_copy_native(struct GNUNET_NETWORK_FDSet *to, const fd_set *from, int nfds)
Copy a native fd set into the GNUnet representation.
Definition network.c:1040
struct GNUNET_NETWORK_FDSet * GNUNET_NETWORK_fdset_create(void)
Creates an fd set.
Definition network.c:1168
void GNUNET_PEERSTORE_monitor_stop(struct GNUNET_PEERSTORE_Monitor *zm)
Stop monitoring.
void GNUNET_PEERSTORE_disconnect(struct GNUNET_PEERSTORE_Handle *h)
Disconnect from the PEERSTORE service.
struct GNUNET_PEERSTORE_Monitor * GNUNET_PEERSTORE_monitor_start(const struct GNUNET_CONFIGURATION_Handle *cfg, int iterate_first, const char *sub_system, const struct GNUNET_PeerIdentity *peer, const char *key, GNUNET_SCHEDULER_TaskCallback error_cb, void *error_cb_cls, GNUNET_SCHEDULER_TaskCallback sync_cb, void *sync_cb_cls, GNUNET_PEERSTORE_Processor callback, void *callback_cls)
Request watching a given key The monitoring can be filtered to contain only records matching peer and...
struct GNUNET_PEERSTORE_Handle * GNUNET_PEERSTORE_connect(const struct GNUNET_CONFIGURATION_Handle *cfg)
Connect to the PEERSTORE service.
void GNUNET_PEERSTORE_monitor_next(struct GNUNET_PEERSTORE_Monitor *zm, uint64_t limit)
Calls the monitor processor specified in GNUNET_PEERSTORE_monitor_start for the next record(s).
#define GNUNET_PEERSTORE_HELLO_KEY
Key used for storing HELLO in the peerstore.
#define GNUNET_MESSAGE_TYPE_HOSTLIST_ADVERTISEMENT
Hostlist advertisement message.
char * GNUNET_RESOLVER_local_fqdn_get(void)
Get local fully qualified domain name.
struct GNUNET_SCHEDULER_Task * GNUNET_SCHEDULER_add_select(enum GNUNET_SCHEDULER_Priority prio, struct GNUNET_TIME_Relative delay, const struct GNUNET_NETWORK_FDSet *rs, const struct GNUNET_NETWORK_FDSet *ws, GNUNET_SCHEDULER_TaskCallback task, void *task_cls)
Schedule a new task to be run with a specified delay or when any of the specified file descriptor set...
Definition scheduler.c:1841
void * GNUNET_SCHEDULER_cancel(struct GNUNET_SCHEDULER_Task *task)
Cancel the task with the specified identifier.
Definition scheduler.c:986
struct GNUNET_SCHEDULER_Task * GNUNET_SCHEDULER_add_delayed(struct GNUNET_TIME_Relative delay, GNUNET_SCHEDULER_TaskCallback task, void *task_cls)
Schedule a new task to be run with a specified delay.
Definition scheduler.c:1283
void GNUNET_STATISTICS_set(struct GNUNET_STATISTICS_Handle *handle, const char *name, uint64_t value, int make_persistent)
Set statistic value for the peer.
void GNUNET_STATISTICS_update(struct GNUNET_STATISTICS_Handle *handle, const char *name, int64_t delta, int make_persistent)
Set statistic value for the peer.
#define GNUNET_TIME_UNIT_FOREVER_REL
Constant used to specify "forever".
#define GNUNET_TIME_UNIT_MINUTES
One minute.
#define max(x, y)
static unsigned int size
Size of the "table".
Definition peer.c:68
#define _(String)
GNU gettext support macro.
Definition platform.h:179
static struct GNUNET_MQ_Handle * mq
Our connection to the resolver service, created on-demand, but then persists until error or shutdown.
Context for the core service connection.
Definition core_api.c:78
Context for parsing HELLOs.
Definition hello-uri.c:233
Handle to a message queue.
Definition mq.c:87
Header for all communications.
collection of IO descriptors
The identity of the host (wraps the signing key of the peer).
Entry in list of pending tasks.
Definition scheduler.c:141
Handle for the service.
Time for relative time used by GNUnet, in microseconds.
Context for host_processor().
char * data
Place where we accumulate all of the HELLO messages.
unsigned int size
Number of bytes in data.

Function Documentation

◆ add_cors_headers()

static void add_cors_headers ( struct MHD_Response *  resp)
static

Add headers to a request indicating that we allow Cross-Origin Resource Sharing.

Parameters
responseresponse to add headers to

Definition at line 155 of file gnunet-daemon-hostlist_server.c.

156{
157 GNUNET_assert (MHD_NO !=
158 MHD_add_response_header (resp,
159 "Access-Control-Allow-Origin", "*"));
160 GNUNET_assert (MHD_NO !=
161 MHD_add_response_header (resp,
162 "Access-Control-Allow-Methods",
163 "GET, OPTIONS"));
164 GNUNET_assert (MHD_NO !=
165 MHD_add_response_header (resp, "Access-Control-Max-Age",
166 "86400"));
167}

References GNUNET_assert.

Referenced by access_handler_callback(), and finish_response().

Here is the caller graph for this function:

◆ build_json_response()

static struct MHD_Response * build_json_response ( const struct HostSet host_set)
static

Definition at line 171 of file gnunet-daemon-hostlist_server.c.

172{
173 struct GNUNET_MessageHeader *hello;
174 struct GNUNET_HELLO_Parser *hparser;
175 json_t*hello_uri_j;
176 json_t*hello_array;
177 char *hello_uri;
178 char *hello_uris;
179 size_t offset = 0;
180
181 hello_uri_j = json_object ();
182 hello_array = json_array ();
183 while (offset < host_set->size)
184 {
185 hello = (struct GNUNET_MessageHeader*) (host_set->data + offset);
186 hparser = GNUNET_HELLO_parser_from_msg (hello, NULL);
187 if (NULL == hparser)
188 {
190 "HELLO from host set malformed, skipping...\n");
191 offset += ntohs (hello->size);
192 continue;
193 }
194 hello_uri = GNUNET_HELLO_parser_to_url (hparser);
195 json_array_append_new (hello_array, json_string (hello_uri));
196 GNUNET_free (hello_uri);
197 GNUNET_HELLO_parser_free (hparser);
198 offset += ntohs (hello->size);
199 }
200 json_object_set_new (hello_uri_j, "hellos", hello_array);
201 hello_uris = json_dumps (hello_uri_j, JSON_INDENT (2));
202 json_decref (hello_uri_j);
203 return MHD_create_response_from_buffer (strlen (hello_uris),
204 hello_uris,
205 MHD_RESPMEM_MUST_FREE);
206}

References HostSet::data, GNUNET_ERROR_TYPE_WARNING, GNUNET_free, GNUNET_HELLO_parser_free(), GNUNET_HELLO_parser_from_msg(), GNUNET_HELLO_parser_to_url(), GNUNET_log, GNUNET_MessageHeader::size, and size.

Referenced by finish_response().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ finish_response()

static void finish_response ( )
static

Function that assembles our response.

Definition at line 213 of file gnunet-daemon-hostlist_server.c.

214{
215 if (NULL != response)
216 MHD_destroy_response (response);
217 if (NULL != response_json)
218 MHD_destroy_response (response_json);
220 "Creating hostlist response with %u bytes\n",
221 (unsigned int) builder->size);
222 response = MHD_create_response_from_buffer (builder->size,
223 builder->data,
224 MHD_RESPMEM_MUST_FREE);
226 GNUNET_assert (MHD_NO != MHD_add_response_header (response_json,
227 "Content-Type",
228 "application/json"));
230 if ((NULL == daemon_handle_v4) && (NULL == daemon_handle_v6))
231 {
232 MHD_destroy_response (response);
233 response = NULL;
234 MHD_destroy_response (response_json);
235 response_json = NULL;
236 }
238 gettext_noop ("bytes in hostlist"),
239 builder->size,
240 GNUNET_YES);
242 builder = NULL;
243}

References add_cors_headers(), build_json_response(), builder, daemon_handle_v4, daemon_handle_v6, HostSet::data, gettext_noop, GNUNET_assert, GNUNET_ERROR_TYPE_DEBUG, GNUNET_free, GNUNET_log, GNUNET_STATISTICS_set(), GNUNET_YES, response, response_json, HostSet::size, and stats.

Referenced by process_notify().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ host_processor()

static enum GNUNET_GenericReturnValue host_processor ( void *  cls,
const struct GNUNET_PeerIdentity peer,
void *  value 
)
static

Callback that processes each of the known HELLOs for the hostlist response construction.

Parameters
clsclosure, NULL
peerid of the peer, NULL for last call
hellohello message for the peer (can be NULL)
err_msgmessage

Definition at line 256 of file gnunet-daemon-hostlist_server.c.

259{
260 size_t old;
261 size_t s;
262 struct GNUNET_MessageHeader *hello = value;
263 (void) cls;
264
266 "host_processor\n");
267 old = builder->size;
268 s = ntohs (hello->size);
270 "Received %u bytes of `%s' from peer `%s' for hostlist.\n",
271 (unsigned int) s,
272 "HELLO",
273 GNUNET_i2s (peer));
274 if ((old + s >= GNUNET_MAX_MALLOC_CHECKED) ||
275 (old + s >= MAX_BYTES_PER_HOSTLISTS))
276 {
277 /* too large, skip! */
280 "bytes not included in hostlist (size limit)"),
281 s,
282 GNUNET_NO);
283 return GNUNET_YES;
284 }
286 "Adding peer `%s' to hostlist (%u bytes)\n",
287 GNUNET_i2s (peer),
288 (unsigned int) s);
290 GNUNET_memcpy (&builder->data[old], hello, s);
291
292 return GNUNET_YES;
293}

References builder, HostSet::data, gettext_noop, GNUNET_array_grow, GNUNET_ERROR_TYPE_DEBUG, GNUNET_ERROR_TYPE_INFO, GNUNET_i2s(), GNUNET_log, GNUNET_MAX_MALLOC_CHECKED, GNUNET_memcpy, GNUNET_NO, GNUNET_STATISTICS_update(), GNUNET_YES, MAX_BYTES_PER_HOSTLISTS, GNUNET_MessageHeader::size, HostSet::size, stats, and value.

Referenced by process_notify().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ accept_policy_callback()

static MHD_RESULT accept_policy_callback ( void *  cls,
const struct sockaddr *  addr,
socklen_t  addrlen 
)
static

Hostlist access policy (very permissive, allows everything).

Returns #MHD_NO only if we are not yet ready to serve.

Parameters
clsclosure
addraddress information from the client
addrlenlength of addr
Returns
#MHD_YES if connection is allowed, #MHD_NO if not (we are not ready)

Definition at line 306 of file gnunet-daemon-hostlist_server.c.

309{
310 if (NULL == response)
311 {
312 GNUNET_log (
314 "Received request for hostlist, but I am not yet ready; rejecting!\n");
315 return MHD_NO;
316 }
317 return MHD_YES; /* accept all */
318}

References GNUNET_ERROR_TYPE_DEBUG, GNUNET_log, and response.

Referenced by GNUNET_HOSTLIST_server_start().

Here is the caller graph for this function:

◆ header_iterator()

static int header_iterator ( void *  cls,
enum MHD_ValueKind  kind,
const char *  key,
const char *  value 
)
static

Definition at line 322 of file gnunet-daemon-hostlist_server.c.

326{
327 enum GNUNET_GenericReturnValue *want_json = cls;
328
329 if (0 != strcasecmp (key, "Accept"))
330 return GNUNET_YES;
331 if (0 == strcasecmp (value, "application/json"))
332 *want_json = GNUNET_YES;
333 return MHD_YES;
334}

References GNUNET_YES, key, and value.

Referenced by access_handler_callback().

Here is the caller graph for this function:

◆ access_handler_callback()

static MHD_RESULT access_handler_callback ( void *  cls,
struct MHD_Connection *  connection,
const char *  url,
const char *  method,
const char *  version,
const char *  upload_data,
size_t *  upload_data_size,
void **  con_cls 
)
static

Main request handler.

Parameters
clsargument given together with the function pointer when the handler was registered with MHD
connection
urlthe requested url
methodthe HTTP method used (#MHD_HTTP_METHOD_GET, #MHD_HTTP_METHOD_PUT, etc.)
versionthe HTTP version string (e.g. #MHD_HTTP_VERSION_1_1)
upload_datathe data being uploaded (excluding HEADERS, for a POST that fits into memory and that is encoded with a supported encoding, the POST data will NOT be given in upload_data and is instead available as part of #MHD_get_connection_values; very large POST data will be made available incrementally in upload_data)
upload_data_sizeset initially to the size of the upload_data provided; the method must update this value to the number of bytes NOT processed;
con_clspointer that the callback can set to some address and that will be preserved by MHD for future calls for this request; since the access handler may be called many times (e.g. for a PUT/POST operation with plenty of upload data) this allows the application to easily associate some request-specific state. If necessary, this state can be cleaned up in the global #MHD_RequestCompletedCallback (which can be set with the #MHD_OPTION_NOTIFY_COMPLETED). Initially, *con_cls will be NULL.
Returns
#MHD_YES if the connection was handled successfully, #MHD_NO if the socket must be closed due to a serious error while handling the request

Definition at line 373 of file gnunet-daemon-hostlist_server.c.

381{
382 static int dummy;
383 struct MHD_Response *selected_response;
384 enum GNUNET_GenericReturnValue want_json = GNUNET_NO;
385
386 /* CORS pre-flight request */
387 if (0 == strcmp (MHD_HTTP_METHOD_OPTIONS, method))
388 {
389 struct MHD_Response *options_response;
390 int rc;
391
392 options_response =
393 MHD_create_response_from_buffer (0, NULL, MHD_RESPMEM_PERSISTENT);
394 add_cors_headers (options_response);
395 rc = MHD_queue_response (connection, MHD_HTTP_OK, options_response);
396 MHD_destroy_response (options_response);
397 return rc;
398 }
399 if (0 != strcmp (method, MHD_HTTP_METHOD_GET))
400 {
402 _ ("Refusing `%s' request to hostlist server\n"),
403 method);
406 "hostlist requests refused (not HTTP GET)"),
407 1,
408 GNUNET_YES);
409 return MHD_NO;
410 }
411 if (NULL == *con_cls)
412 {
413 (*con_cls) = &dummy;
414 return MHD_YES;
415 }
416 if (0 != *upload_data_size)
417 {
419 _ ("Refusing `%s' request with %llu bytes of upload data\n"),
420 method,
421 (unsigned long long) *upload_data_size);
424 "hostlist requests refused (upload data)"),
425 1,
426 GNUNET_YES);
427 return MHD_NO; /* do not support upload data */
428 }
429 selected_response = response;
430 MHD_get_connection_values (connection,
431 MHD_HEADER_KIND,
432 (MHD_KeyValueIterator) & header_iterator,
433 &want_json);
434 if (GNUNET_YES == want_json)
435 {
436 selected_response = response_json;
437 }
438 if (NULL == selected_response)
439 {
440 GNUNET_log (
442 _ (
443 "Could not handle hostlist request since I do not have a response yet\n"));
446 "hostlist requests refused (not ready)"),
447 1,
448 GNUNET_YES);
449 return MHD_NO; /* internal error, no response yet */
450 }
452 _ ("Received request for our hostlist\n"));
454 gettext_noop ("hostlist requests processed"),
455 1,
456 GNUNET_YES);
457 return MHD_queue_response (connection, MHD_HTTP_OK, selected_response);
458}

References _, add_cors_headers(), dummy, gettext_noop, GNUNET_ERROR_TYPE_INFO, GNUNET_ERROR_TYPE_WARNING, GNUNET_log, GNUNET_NO, GNUNET_STATISTICS_update(), GNUNET_YES, header_iterator(), response, response_json, and stats.

Referenced by GNUNET_HOSTLIST_server_start().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ adv_transmit()

static void adv_transmit ( struct GNUNET_MQ_Handle mq)
static

Handler called by CORE when CORE is ready to transmit message.

Parameters
clsclosure with the const struct GNUNET_PeerIdentity * of the peer we are sending to
sizesize of buffer to copy message to
bufbuffer to copy message to
Returns
number of bytes copied to buf

Definition at line 471 of file gnunet-daemon-hostlist_server.c.

472{
473 static uint64_t hostlist_adv_count;
474 size_t uri_size; /* Including \0 termination! */
475 struct GNUNET_MessageHeader *header;
476 struct GNUNET_MQ_Envelope *env;
477
478 uri_size = strlen (hostlist_uri) + 1;
479 env = GNUNET_MQ_msg_extra (header,
480 uri_size,
482 GNUNET_memcpy (&header[1], hostlist_uri, uri_size);
488 "Sent advertisement message: Copied %u bytes into buffer!\n",
489 (unsigned int) uri_size);
490 hostlist_adv_count++;
492 " # Sent advertisement message: %llu\n",
493 (unsigned long long) hostlist_adv_count);
495 gettext_noop ("# hostlist advertisements send"),
496 1,
497 GNUNET_NO);
498}

References env, gettext_noop, GNUNET_ERROR_TYPE_DEBUG, GNUNET_log, GNUNET_memcpy, GNUNET_MESSAGE_TYPE_HOSTLIST_ADVERTISEMENT, GNUNET_MQ_env_set_options(), GNUNET_MQ_msg_extra, GNUNET_MQ_PREF_CORK_ALLOWED, GNUNET_MQ_PREF_UNRELIABLE, GNUNET_MQ_send(), GNUNET_NO, GNUNET_STATISTICS_update(), hostlist_uri, mq, and stats.

Referenced by connect_handler().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ connect_handler()

static void * connect_handler ( void *  cls,
const struct GNUNET_PeerIdentity peer,
struct GNUNET_MQ_Handle mq,
enum GNUNET_CORE_PeerClass  class 
)
static

Method called whenever a given peer connects.

Parameters
clsclosure
peerpeer identity this notification is about
mqqueue for transmission to peer
classclass of the connecting peer
Returns
NULL (must!)

Definition at line 511 of file gnunet-daemon-hostlist_server.c.

515{
516 size_t size;
517
518 if (! advertising)
519 return NULL;
520 if (NULL == hostlist_uri)
521 return NULL;
522 size = strlen (hostlist_uri) + 1;
523 if (size + sizeof(struct GNUNET_MessageHeader) >= GNUNET_MAX_MESSAGE_SIZE)
524 {
525 GNUNET_break (0);
526 return NULL;
527 }
528 size += sizeof(struct GNUNET_MessageHeader);
529 if (NULL == core)
530 {
531 GNUNET_break (0);
532 return NULL;
533 }
534 GNUNET_log (
536 "Asked CORE to transmit advertisement message with a size of %u bytes to peer `%s'\n",
537 (unsigned int) size,
538 GNUNET_i2s (peer));
540 return NULL;
541}

References adv_transmit(), advertising, core, GNUNET_break, GNUNET_ERROR_TYPE_DEBUG, GNUNET_i2s(), GNUNET_log, GNUNET_MAX_MESSAGE_SIZE, hostlist_uri, mq, and size.

Referenced by GNUNET_HOSTLIST_server_start().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ process_notify()

static void process_notify ( void *  cls,
const struct GNUNET_PEERSTORE_Record record,
const char *  err_msg 
)
static

PEERSTORE calls this function to let us know about a possible peer that we might want to connect to.

Parameters
clsclosure (not used)
peerpotential peer to connect to
helloHELLO for this peer (or NULL)
err_msgNULL if successful, otherwise contains error message

Definition at line 554 of file gnunet-daemon-hostlist_server.c.

557{
558 unsigned int map_size;
559 struct GNUNET_MessageHeader *hello_cpy;
560 struct GNUNET_PeerIdentity *peer_cpy;
561 struct GNUNET_MessageHeader *hello;
562
565 "Peerstore is notifying us to rebuild our hostlist map size %u\n",
566 map_size);
567 if (NULL != err_msg)
568 {
570 _ ("Error in communication with PEERSTORE service: %s\n"),
571 err_msg);
573 return;
574 }
575 if (NULL == record)
576 {
577 GNUNET_break (0);
579 return;
580 }
581 hello = record->value;
582 /* @e value and @e value_size are independent, and the HELLO is an
583 unvalidated blob a remote peer published: a zero-length value leaves
584 @a hello NULL, and a @e size field larger than @e value_size makes the
585 GNUNET_memcpy() below read past the end of the record. */
586 if ((NULL == hello) ||
587 (record->value_size < sizeof (*hello)) ||
588 (ntohs (hello->size) > record->value_size))
589 {
590 GNUNET_break_op (0);
592 return;
593 }
594 if (NULL != builder)
595 {
597 builder->size = 0;
598 builder->data = NULL;
599 }
600 else
601 {
602 builder = GNUNET_new (struct HostSet);
603 }
604
605 peer_cpy = GNUNET_malloc (sizeof (struct GNUNET_PeerIdentity));
606 GNUNET_memcpy (peer_cpy, &record->peer, sizeof (struct GNUNET_PeerIdentity));
607 hello_cpy = GNUNET_malloc (ntohs (hello->size));
608 GNUNET_memcpy (hello_cpy, hello, ntohs (hello->size));
611 peer_cpy,
612 (struct
614 hello_cpy,
618 NULL))
622 "1 Peerstore is notifying us to rebuild our hostlist map size %u peer %s\n",
623 map_size,
624 GNUNET_i2s (&record->peer));
626}

References _, builder, HostSet::data, finish_response(), GNUNET_assert, GNUNET_break, GNUNET_break_op, GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE, GNUNET_CONTAINER_multipeermap_iterate(), GNUNET_CONTAINER_multipeermap_put(), GNUNET_CONTAINER_multipeermap_size(), GNUNET_ERROR_TYPE_DEBUG, GNUNET_ERROR_TYPE_INFO, GNUNET_free, GNUNET_i2s(), GNUNET_log, GNUNET_malloc, GNUNET_memcpy, GNUNET_new, GNUNET_PEERSTORE_monitor_next(), GNUNET_YES, hellos, host_processor(), map_size, peerstore_notify, record(), GNUNET_MessageHeader::size, and HostSet::size.

Referenced by start_notify().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ prepare_daemon()

static struct GNUNET_SCHEDULER_Task * prepare_daemon ( struct MHD_Daemon *  daemon_handle)
static

Function that queries MHD's select sets and starts the task waiting for them.

Parameters
daemon_handleHTTP server to prepare to run

Definition at line 667 of file gnunet-daemon-hostlist_server.c.

668{
670 fd_set rs;
671 fd_set ws;
672 fd_set es;
673 struct GNUNET_NETWORK_FDSet *wrs;
674 struct GNUNET_NETWORK_FDSet *wws;
675 int max;
676 MHD_UNSIGNED_LONG_LONG timeout;
677 int haveto;
678 struct GNUNET_TIME_Relative tv;
679
680 FD_ZERO (&rs);
681 FD_ZERO (&ws);
682 FD_ZERO (&es);
685 max = -1;
686 GNUNET_assert (MHD_YES == MHD_get_fdset (daemon_handle, &rs, &ws, &es, &max));
687 haveto = MHD_get_timeout (daemon_handle, &timeout);
688 if (haveto == MHD_YES)
689 tv.rel_value_us = (uint64_t) timeout * 1000LL;
690 else
695 tv,
696 wrs,
697 wws,
698 &run_daemon,
699 daemon_handle);
702 return ret;
703}

References GNUNET_assert, GNUNET_NETWORK_fdset_copy_native(), GNUNET_NETWORK_fdset_create(), GNUNET_NETWORK_fdset_destroy(), GNUNET_SCHEDULER_add_select(), GNUNET_SCHEDULER_PRIORITY_HIGH, GNUNET_TIME_UNIT_FOREVER_REL, max, GNUNET_TIME_Relative::rel_value_us, ret, run_daemon(), and timeout.

Referenced by GNUNET_HOSTLIST_server_start(), and run_daemon().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ run_daemon()

static void run_daemon ( void *  cls)
static

Call MHD to process pending requests and then go back and schedule the next run.

Parameters
clsthe struct MHD_Daemon of the HTTP server to run

Definition at line 644 of file gnunet-daemon-hostlist_server.c.

645{
646 struct MHD_Daemon *daemon_handle = cls;
647
648 if (daemon_handle == daemon_handle_v4)
649 hostlist_task_v4 = NULL;
650 else
651 hostlist_task_v6 = NULL;
652 GNUNET_assert (MHD_YES == MHD_run (daemon_handle));
653 if (daemon_handle == daemon_handle_v4)
654 hostlist_task_v4 = prepare_daemon (daemon_handle);
655 else
656 hostlist_task_v6 = prepare_daemon (daemon_handle);
657}

References daemon_handle_v4, GNUNET_assert, hostlist_task_v4, hostlist_task_v6, and prepare_daemon().

Referenced by prepare_daemon().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ error_cb()

static void error_cb ( void *  cls)
static

Definition at line 707 of file gnunet-daemon-hostlist_server.c.

708{
710 "Error in PEERSTORE monitoring\n");
711}

References GNUNET_ERROR_TYPE_WARNING, and GNUNET_log.

Referenced by start_notify().

Here is the caller graph for this function:

◆ sync_cb()

static void sync_cb ( void *  cls)
static

Definition at line 715 of file gnunet-daemon-hostlist_server.c.

716{
718 "Done with initial PEERSTORE iteration during monitoring\n");
719}

References GNUNET_ERROR_TYPE_WARNING, and GNUNET_log.

Referenced by start_notify().

Here is the caller graph for this function:

◆ start_notify()

static void start_notify ( void *  cls)
static

Definition at line 723 of file gnunet-daemon-hostlist_server.c.

724{
725 (void) cls;
726
728 "Starting to process new hellos to add to hostlist.\n");
731 "peerstore",
732 NULL,
734 &error_cb,
735 NULL,
736 &sync_cb,
737 NULL,
738 &process_notify, NULL);
739}

References cfg, error_cb(), GNUNET_ERROR_TYPE_DEBUG, GNUNET_log, GNUNET_PEERSTORE_HELLO_KEY, GNUNET_PEERSTORE_monitor_start(), GNUNET_YES, peerstore_notify, process_notify(), and sync_cb().

Referenced by GNUNET_HOSTLIST_server_start().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ GNUNET_HOSTLIST_server_start()

int GNUNET_HOSTLIST_server_start ( const struct GNUNET_CONFIGURATION_Handle c,
struct GNUNET_STATISTICS_Handle st,
struct GNUNET_CORE_Handle co,
GNUNET_CORE_ConnectEventHandler server_ch,
int  advertise 
)

Start server offering our hostlist.

Parameters
cconfiguration to use
ststatistics handle to use
cocore handle to use
[out]server_chset to handler for CORE connect events
advertiseGNUNET_YES if we should advertise our hostlist
Returns
GNUNET_OK on success

Definition at line 753 of file gnunet-daemon-hostlist_server.c.

758{
759 unsigned long long port;
760 char *hostname;
761 char *ipv4;
762 char *ipv6;
763 size_t size;
764 struct in_addr i4;
765 struct in6_addr i6;
766 struct sockaddr_in v4;
767 struct sockaddr_in6 v6;
768 const struct sockaddr *sa4;
769 const struct sockaddr *sa6;
770
772 advertising = advertise;
773 if (! advertising)
774 {
776 "Advertising not enabled on this hostlist server\n");
777 }
778 else
779 {
781 "Advertising enabled on this hostlist server\n");
782 }
783 cfg = c;
784 stats = st;
786 if (NULL == peerstore)
787 {
789 _ ("Could not access PEERSTORE service. Exiting.\n"));
790 return GNUNET_SYSERR;
791 }
793 "HOSTLIST",
794 "HTTPPORT",
795 &port))
796 return GNUNET_SYSERR;
797 if ((0 == port) || (port > UINT16_MAX))
798 {
800 _ ("Invalid port number %llu. Exiting.\n"),
801 port);
802 return GNUNET_SYSERR;
803 }
804
805 if (GNUNET_SYSERR ==
807 "HOSTLIST",
808 "EXTERNAL_DNS_NAME",
809 &hostname))
810 hostname = GNUNET_RESOLVER_local_fqdn_get ();
812 _ ("Hostlist service starts on %s:%llu\n"),
813 hostname,
814 port);
815 if (NULL != hostname)
816 {
817 size = strlen (hostname);
818 if (size + 15 > MAX_URL_LEN)
819 {
820 GNUNET_break (0);
821 }
822 else
823 {
825 "http://%s:%u/",
826 hostname,
827 (unsigned int) port);
829 _ ("Address to obtain hostlist: `%s'\n"),
831 }
832 GNUNET_free (hostname);
833 }
834
835 if (GNUNET_CONFIGURATION_have_value (cfg, "HOSTLIST", "BINDTOIPV4"))
836 {
838 "HOSTLIST",
839 "BINDTOIP",
840 &ipv4))
841 {
842 GNUNET_log (
844 _ ("BINDTOIP does not a valid IPv4 address! Ignoring BINDTOIPV4.\n"));
845 }
846 }
847 else
848 ipv4 = NULL;
849 if (GNUNET_CONFIGURATION_have_value (cfg, "HOSTLIST", "BINDTOIPV6"))
850 {
852 "HOSTLIST",
853 "BINDTOIP",
854 &ipv6))
855 {
856 GNUNET_log (
858 _ ("BINDTOIP does not a valid IPv4 address! Ignoring BINDTOIPV6.\n"));
859 }
860 }
861 else
862 ipv6 = NULL;
863 sa4 = NULL;
864 if (NULL != ipv4)
865 {
866 if (1 == inet_pton (AF_INET, ipv4, &i4))
867 {
868 memset (&v4, 0, sizeof(v4));
869 v4.sin_family = AF_INET;
870 v4.sin_addr = i4;
871 v4.sin_port = htons (port);
872#if HAVE_SOCKADDR_IN_SIN_LEN
873 v4.sin_len = sizeof(v4);
874#endif
875 sa4 = (const struct sockaddr *) &v4;
876 }
877 else
879 _ (
880 "`%s' is not a valid IPv4 address! Ignoring BINDTOIPV4.\n"),
881 ipv4);
883 }
884 sa6 = NULL;
885 if (NULL != ipv6)
886 {
887 if (1 == inet_pton (AF_INET6, ipv6, &i6))
888 {
889 memset (&v6, 0, sizeof(v6));
890 v6.sin6_family = AF_INET6;
891 v6.sin6_addr = i6;
892 v6.sin6_port = htons (port);
893#if HAVE_SOCKADDR_IN_SIN_LEN
894 v6.sin6_len = sizeof(v6);
895#endif
896 sa6 = (const struct sockaddr *) &v6;
897 }
898 else
900 _ (
901 "`%s' is not a valid IPv6 address! Ignoring BINDTOIPV6.\n"),
902 ipv6);
904 }
905
906 daemon_handle_v6 = MHD_start_daemon (MHD_USE_IPv6 | MHD_USE_DEBUG,
907 (uint16_t) port,
909 NULL,
911 NULL,
912 MHD_OPTION_CONNECTION_LIMIT,
913 (unsigned int) 128,
914 MHD_OPTION_PER_IP_CONNECTION_LIMIT,
915 (unsigned int) 32,
916 MHD_OPTION_CONNECTION_TIMEOUT,
917 (unsigned int) 16,
918 MHD_OPTION_CONNECTION_MEMORY_LIMIT,
919 (size_t) (16 * 1024),
920 MHD_OPTION_SOCK_ADDR,
921 sa6,
922 MHD_OPTION_END);
923 daemon_handle_v4 = MHD_start_daemon (MHD_NO_FLAG | MHD_USE_DEBUG,
924 (uint16_t) port,
926 NULL,
928 NULL,
929 MHD_OPTION_CONNECTION_LIMIT,
930 (unsigned int) 128,
931 MHD_OPTION_PER_IP_CONNECTION_LIMIT,
932 (unsigned int) 32,
933 MHD_OPTION_CONNECTION_TIMEOUT,
934 (unsigned int) 16,
935 MHD_OPTION_CONNECTION_MEMORY_LIMIT,
936 (size_t) (16 * 1024),
937 MHD_OPTION_SOCK_ADDR,
938 sa4,
939 MHD_OPTION_END);
940
941 if ((NULL == daemon_handle_v6) && (NULL == daemon_handle_v4))
942 {
944 _ ("Could not start hostlist HTTP server on port %u\n"),
945 (unsigned short) port);
946 return GNUNET_SYSERR;
947 }
948
949 core = co;
951 if (NULL != daemon_handle_v4)
953 if (NULL != daemon_handle_v6)
958 NULL);
959 return GNUNET_OK;
960}

References _, accept_policy_callback(), access_handler_callback(), advertising, cfg, connect_handler(), core, daemon_handle_v4, daemon_handle_v6, GNUNET_asprintf(), GNUNET_break, GNUNET_CONFIGURATION_get_value_number(), GNUNET_CONFIGURATION_get_value_string(), GNUNET_CONFIGURATION_have_value(), GNUNET_CONTAINER_multipeermap_create(), GNUNET_ERROR_TYPE_DEBUG, GNUNET_ERROR_TYPE_ERROR, GNUNET_ERROR_TYPE_INFO, GNUNET_ERROR_TYPE_WARNING, GNUNET_free, GNUNET_log, GNUNET_OK, GNUNET_PEERSTORE_connect(), GNUNET_RESOLVER_local_fqdn_get(), GNUNET_SCHEDULER_add_delayed(), GNUNET_SYSERR, GNUNET_TIME_UNIT_MINUTES, GNUNET_YES, hellos, hostlist_task_v4, hostlist_task_v6, hostlist_uri, ipv4, ipv6, MAX_URL_LEN, peerstore, peerstore_notify_task, port, prepare_daemon(), server_ch, size, st, start_notify(), and stats.

Referenced by run().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ GNUNET_HOSTLIST_server_stop()

void GNUNET_HOSTLIST_server_stop ( void  )

Stop server offering our hostlist.

Definition at line 967 of file gnunet-daemon-hostlist_server.c.

968{
969 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Hostlist server shutdown\n");
970 if (NULL != hostlist_task_v6)
971 {
973 hostlist_task_v6 = NULL;
974 }
975 if (NULL != hostlist_task_v4)
976 {
978 hostlist_task_v4 = NULL;
979 }
980 if (NULL != daemon_handle_v4)
981 {
982 MHD_stop_daemon (daemon_handle_v4);
983 daemon_handle_v4 = NULL;
984 }
985 if (NULL != daemon_handle_v6)
986 {
987 MHD_stop_daemon (daemon_handle_v6);
988 daemon_handle_v6 = NULL;
989 }
990 if (NULL != response)
991 {
992 MHD_destroy_response (response);
993 response = NULL;
994 }
995 if (NULL != response_json)
996 {
997 MHD_destroy_response (response_json);
998 response_json = NULL;
999 }
1000 if (NULL != peerstore_notify)
1001 {
1003 peerstore_notify = NULL;
1004 }
1005 else if (NULL != peerstore_notify_task)
1006 {
1008 }
1009 if (NULL != builder)
1010 {
1013 builder = NULL;
1014 }
1015 if (NULL != peerstore)
1016 {
1018 peerstore = NULL;
1019 }
1020 cfg = NULL;
1021 stats = NULL;
1022 core = NULL;
1023}

References builder, cfg, core, daemon_handle_v4, daemon_handle_v6, HostSet::data, GNUNET_ERROR_TYPE_DEBUG, GNUNET_free, GNUNET_log, GNUNET_PEERSTORE_disconnect(), GNUNET_PEERSTORE_monitor_stop(), GNUNET_SCHEDULER_cancel(), hostlist_task_v4, hostlist_task_v6, peerstore, peerstore_notify, peerstore_notify_task, response, response_json, and stats.

Referenced by cleaning_task().

Here is the call graph for this function:
Here is the caller graph for this function:

Variable Documentation

◆ hellos

Map with hellos we build the hostlist with.

Definition at line 50 of file gnunet-daemon-hostlist_server.c.

Referenced by GNUNET_HOSTLIST_server_start(), and process_notify().

◆ daemon_handle_v6

struct MHD_Daemon* daemon_handle_v6
static

Handle to the HTTP server as provided by libmicrohttpd for IPv6.

Definition at line 55 of file gnunet-daemon-hostlist_server.c.

Referenced by finish_response(), GNUNET_HOSTLIST_server_start(), and GNUNET_HOSTLIST_server_stop().

◆ daemon_handle_v4

struct MHD_Daemon* daemon_handle_v4
static

Handle to the HTTP server as provided by libmicrohttpd for IPv4.

Definition at line 60 of file gnunet-daemon-hostlist_server.c.

Referenced by finish_response(), GNUNET_HOSTLIST_server_start(), GNUNET_HOSTLIST_server_stop(), and run_daemon().

◆ cfg

const struct GNUNET_CONFIGURATION_Handle* cfg
static

Our configuration.

Definition at line 65 of file gnunet-daemon-hostlist_server.c.

Referenced by GNUNET_HOSTLIST_server_start(), GNUNET_HOSTLIST_server_stop(), and start_notify().

◆ stats

◆ core

struct GNUNET_CORE_Handle* core
static

Handle to the core service (NULL until we've connected to it).

Definition at line 75 of file gnunet-daemon-hostlist_server.c.

Referenced by connect_handler(), GNUNET_HOSTLIST_server_start(), and GNUNET_HOSTLIST_server_stop().

◆ peerstore_notify_task

struct GNUNET_SCHEDULER_Task* peerstore_notify_task

The task to delayed start the notification process initially.

We like to give transport some time to give us our hello to distribute it.

Definition at line 81 of file gnunet-daemon-hostlist_server.c.

Referenced by GNUNET_HOSTLIST_server_start(), and GNUNET_HOSTLIST_server_stop().

◆ peerstore_notify

struct GNUNET_PEERSTORE_Monitor* peerstore_notify
static

Our peerstore notification context.

We use notification to instantly learn about new peers as they are discovered.

Definition at line 87 of file gnunet-daemon-hostlist_server.c.

Referenced by GNUNET_HOSTLIST_server_stop(), process_notify(), and start_notify().

◆ hostlist_task_v4

struct GNUNET_SCHEDULER_Task* hostlist_task_v4
static

Our primary task for IPv4.

Definition at line 92 of file gnunet-daemon-hostlist_server.c.

Referenced by GNUNET_HOSTLIST_server_start(), GNUNET_HOSTLIST_server_stop(), and run_daemon().

◆ hostlist_task_v6

struct GNUNET_SCHEDULER_Task* hostlist_task_v6
static

Our primary task for IPv6.

Definition at line 97 of file gnunet-daemon-hostlist_server.c.

Referenced by GNUNET_HOSTLIST_server_start(), GNUNET_HOSTLIST_server_stop(), and run_daemon().

◆ response

◆ response_json

struct MHD_Response* response_json
static

Our json response.

Definition at line 107 of file gnunet-daemon-hostlist_server.c.

Referenced by access_handler_callback(), finish_response(), and GNUNET_HOSTLIST_server_stop().

◆ peerstore

struct GNUNET_PEERSTORE_Handle* peerstore
static

Handle to the PEERSTORE service.

Definition at line 112 of file gnunet-daemon-hostlist_server.c.

Referenced by GNUNET_HOSTLIST_server_start(), and GNUNET_HOSTLIST_server_stop().

◆ advertising

int advertising
static

Set if we are allowed to advertise our hostlist to others.

Definition at line 117 of file gnunet-daemon-hostlist_server.c.

Referenced by connect_handler(), and GNUNET_HOSTLIST_server_start().

◆ hostlist_uri

char* hostlist_uri
static

Buffer for the hostlist address.

Definition at line 122 of file gnunet-daemon-hostlist_server.c.

Referenced by adv_transmit(), connect_handler(), and GNUNET_HOSTLIST_server_start().

◆ builder