GNUnet  0.17.6
client.c
Go to the documentation of this file.
1 /*
2  This file is part of GNUnet.
3  Copyright (C) 2001-2016, 2019 GNUnet e.V.
4 
5  GNUnet is free software: you can redistribute it and/or modify it
6  under the terms of the GNU Affero General Public License as published
7  by the Free Software Foundation, either version 3 of the License,
8  or (at your option) any later version.
9 
10  GNUnet is distributed in the hope that it will be useful, but
11  WITHOUT ANY WARRANTY; without even the implied warranty of
12  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13  Affero General Public License for more details.
14 
15  You should have received a copy of the GNU Affero General Public License
16  along with this program. If not, see <http://www.gnu.org/licenses/>.
17 
18  SPDX-License-Identifier: AGPL3.0-or-later
19  */
20 
29 #include "platform.h"
30 #include "gnunet_protocols.h"
31 #include "gnunet_util_lib.h"
33 #include "gnunet_socks.h"
34 
35 
36 #define LOG(kind, ...) GNUNET_log_from (kind, "util-client", __VA_ARGS__)
37 
44 #define CONNECT_RETRY_TIMEOUT GNUNET_TIME_relative_multiply ( \
45  GNUNET_TIME_UNIT_SECONDS, 5)
46 
47 
51 struct ClientState;
52 
53 
58 struct AddressProbe
59 {
63  struct AddressProbe *next;
64 
68  struct AddressProbe *prev;
69 
73  const struct sockaddr *addr;
74 
79 
84 
88  socklen_t addrlen;
89 
94 };
95 
96 
100 struct ClientState
101 {
106 
111 
116 
122 
128 
133 
137  char *hostname;
138 
142  const struct GNUNET_MessageHeader *msg;
143 
148 
153 
158 
163 
168 
173 
179 
183  unsigned long long port;
184 
188  size_t msg_off;
189 
193  unsigned int attempts;
194 
201 };
202 
203 
209 static void
210 start_connect (void *cls);
211 
212 
219 static void
221 {
222  GNUNET_break (NULL == cstate->ap_head);
223  GNUNET_break (NULL == cstate->ap_tail);
224  GNUNET_break (NULL == cstate->dns_active);
225  GNUNET_break (NULL == cstate->sock);
226  GNUNET_assert (NULL == cstate->send_task);
227  GNUNET_assert (NULL == cstate->recv_task);
228  // GNUNET_assert (NULL == cstate->proxy_handshake);
229 
230  cstate->back_off = GNUNET_TIME_STD_BACKOFF (cstate->back_off);
232  "Failed to establish connection to `%s', no further addresses to try, will try again in %s.\n",
233  cstate->service_name,
235  GNUNET_YES));
236  cstate->retry_task
238  &start_connect,
239  cstate);
240 }
241 
242 
248 static void
249 transmit_ready (void *cls)
250 {
251  struct ClientState *cstate = cls;
252  ssize_t ret;
253  size_t len;
254  const char *pos;
255  int notify_in_flight;
256 
257  cstate->send_task = NULL;
258  if (GNUNET_YES == cstate->in_destroy)
259  return;
260  pos = (const char *) cstate->msg;
261  len = ntohs (cstate->msg->size);
262  GNUNET_assert (cstate->msg_off < len);
264  "message of type %u and size %u trying to send with socket %p (MQ: %p\n",
265  ntohs (cstate->msg->type),
266  ntohs (cstate->msg->size),
267  cstate->sock,
268  cstate->mq);
269 
270  RETRY:
272  &pos[cstate->msg_off],
273  len - cstate->msg_off);
274  if ( (-1 == ret) &&
275  ( (EAGAIN == errno) ||
276  (EINTR == errno) ) )
277  {
278  /* ignore */
279  ret = 0;
280  }
281  if (-1 == ret)
282  {
284  "Error during sending message of type %u: %s\n",
285  ntohs (cstate->msg->type),
286  strerror (errno));
287  if (EINTR == errno)
288  {
290  "Retrying message of type %u\n",
291  ntohs (cstate->msg->type));
292  goto RETRY;
293  }
294  GNUNET_MQ_inject_error (cstate->mq,
296  return;
297  }
298  notify_in_flight = (0 == cstate->msg_off);
299  cstate->msg_off += ret;
300  if (cstate->msg_off < len)
301  {
303  "rescheduling message of type %u\n",
304  ntohs (cstate->msg->type));
305  cstate->send_task
307  cstate->sock,
309  cstate);
310  if (notify_in_flight)
312  return;
313  }
315  "sending message of type %u and size %u successful\n",
316  ntohs (cstate->msg->type),
317  ntohs (cstate->msg->size));
318  cstate->msg = NULL;
320 }
321 
322 
333 static int
334 recv_message (void *cls,
335  const struct GNUNET_MessageHeader *msg)
336 {
337  struct ClientState *cstate = cls;
338 
339  if (GNUNET_YES == cstate->in_destroy)
340  return GNUNET_NO;
342  "Received message of type %u and size %u from %s\n",
343  ntohs (msg->type),
344  ntohs (msg->size),
345  cstate->service_name);
346  GNUNET_MQ_inject_message (cstate->mq,
347  msg);
348  if (GNUNET_YES == cstate->in_destroy)
349  return GNUNET_NO;
350  return GNUNET_OK;
351 }
352 
353 
359 static void
360 cancel_aps (struct ClientState *cstate)
361 {
362  struct AddressProbe *pos;
363 
364  while (NULL != (pos = cstate->ap_head))
365  {
370  cstate->ap_tail,
371  pos);
372  GNUNET_free (pos);
373  }
374 }
375 
376 
384 static void
386  void *impl_state)
387 {
388  struct ClientState *cstate = impl_state;
389 
390  (void) mq;
391  if (NULL != cstate->dns_active)
392  {
394  cstate->dns_active = NULL;
395  }
396  if (NULL != cstate->send_task)
397  {
399  cstate->send_task = NULL;
400  }
401  if (NULL != cstate->retry_task)
402  {
404  cstate->retry_task = NULL;
405  }
406  if (GNUNET_SYSERR == cstate->in_destroy)
407  {
408  /* defer destruction */
409  cstate->in_destroy = GNUNET_YES;
410  cstate->mq = NULL;
411  return;
412  }
413  if (NULL != cstate->recv_task)
414  {
416  cstate->recv_task = NULL;
417  }
418  if (NULL != cstate->sock)
419  {
421  "destroying socket: %p\n",
422  cstate->sock);
424  }
425  cancel_aps (cstate);
426  GNUNET_free (cstate->service_name);
427  GNUNET_free (cstate->hostname);
428  GNUNET_MST_destroy (cstate->mst);
429  GNUNET_free (cstate);
430 }
431 
432 
438 static void
439 receive_ready (void *cls)
440 {
441  struct ClientState *cstate = cls;
442  int ret;
443 
444  cstate->recv_task = NULL;
445  cstate->in_destroy = GNUNET_SYSERR;
446  ret = GNUNET_MST_read (cstate->mst,
447  cstate->sock,
448  GNUNET_NO,
449  GNUNET_NO);
450  if (GNUNET_SYSERR == ret)
451  {
452  if (NULL != cstate->mq)
453  GNUNET_MQ_inject_error (cstate->mq,
455  if (GNUNET_YES == cstate->in_destroy)
457  cstate);
458  return;
459  }
460  if (GNUNET_YES == cstate->in_destroy)
461  {
463  cstate);
464  return;
465  }
466  cstate->in_destroy = GNUNET_NO;
467  cstate->recv_task
469  cstate->sock,
470  &receive_ready,
471  cstate);
472 }
473 
474 
480 static void
482 {
483  GNUNET_assert (NULL == cstate->recv_task);
484  cstate->recv_task
486  cstate->sock,
487  &receive_ready,
488  cstate);
489  if (NULL != cstate->msg)
490  {
491  GNUNET_assert (NULL == cstate->send_task);
492  cstate->send_task
494  cstate->sock,
496  cstate);
497  }
498 }
499 
500 
508 static struct GNUNET_NETWORK_Handle *
510  const struct GNUNET_CONFIGURATION_Handle *cfg)
511 {
512 #if AF_UNIX
513  struct GNUNET_NETWORK_Handle *sock;
514  char *unixpath;
515  struct sockaddr_un s_un;
516 
517  unixpath = NULL;
518  if ((GNUNET_OK ==
520  service_name,
521  "UNIXPATH",
522  &unixpath)) &&
523  (0 < strlen (unixpath)))
524  {
525  /* We have a non-NULL unixpath, need to validate it */
526  if (strlen (unixpath) >= sizeof(s_un.sun_path))
527  {
529  _ ("UNIXPATH `%s' too long, maximum length is %llu\n"),
530  unixpath,
531  (unsigned long long) sizeof(s_un.sun_path));
532  unixpath = GNUNET_NETWORK_shorten_unixpath (unixpath);
534  _ ("Using `%s' instead\n"),
535  unixpath);
536  if (NULL == unixpath)
537  return NULL;
538  }
539  memset (&s_un,
540  0,
541  sizeof(s_un));
542  s_un.sun_family = AF_UNIX;
543  GNUNET_strlcpy (s_un.sun_path,
544  unixpath,
545  sizeof(s_un.sun_path));
546 #if HAVE_SOCKADDR_UN_SUN_LEN
547  s_un.sun_len = (u_char) sizeof(struct sockaddr_un);
548 #endif
549  sock = GNUNET_NETWORK_socket_create (AF_UNIX,
550  SOCK_STREAM,
551  0);
552  if ((NULL != sock) &&
553  ((GNUNET_OK ==
555  (struct sockaddr *) &s_un,
556  sizeof(s_un))) ||
557  (EINPROGRESS == errno)))
558  {
560  "Successfully connected to unixpath `%s'!\n",
561  unixpath);
562  GNUNET_free (unixpath);
563  return sock;
564  }
565  if (NULL != sock)
567  }
568  GNUNET_free (unixpath);
569 #endif
570  return NULL;
571 }
572 
573 
580 static void
582 {
583  struct AddressProbe *ap = cls;
584  struct ClientState *cstate = ap->cstate;
585  const struct GNUNET_SCHEDULER_TaskContext *tc;
586  int error;
587  socklen_t len;
588 
589  ap->task = NULL;
590  GNUNET_assert (NULL != ap->sock);
592  cstate->ap_tail,
593  ap);
594  len = sizeof(error);
595  error = 0;
598  (GNUNET_OK !=
600  SOL_SOCKET,
601  SO_ERROR,
602  &error,
603  &len)) ||
604  (0 != error))
605  {
608  GNUNET_free (ap);
609  if ((NULL == cstate->ap_head) &&
610  // (NULL == cstate->proxy_handshake) &&
611  (NULL == cstate->dns_active))
612  connect_fail_continuation (cstate);
613  return;
614  }
616  "Connection to `%s' succeeded!\n",
617  cstate->service_name);
618  /* trigger jobs that waited for the connection */
619  GNUNET_assert (NULL == cstate->sock);
620  cstate->sock = ap->sock;
621  GNUNET_free (ap);
622  cancel_aps (cstate);
624 }
625 
626 
635 static void
637  const struct sockaddr *addr,
638  socklen_t addrlen)
639 {
640  struct ClientState *cstate = cls;
641  struct AddressProbe *ap;
642 
643  if (NULL == addr)
644  {
645  cstate->dns_active = NULL;
646  if ((NULL == cstate->ap_head) &&
647  // (NULL == cstate->proxy_handshake) &&
648  (NULL == cstate->sock))
650  return;
651  }
652  if (NULL != cstate->sock)
653  return; /* already connected */
654  /* try to connect */
656  "Trying to connect using address `%s:%u'\n",
657  GNUNET_a2s (addr,
658  addrlen),
659  (unsigned int) cstate->port);
660  ap = GNUNET_malloc (sizeof(struct AddressProbe) + addrlen);
661  ap->addr = (const struct sockaddr *) &ap[1];
662  GNUNET_memcpy (&ap[1],
663  addr,
664  addrlen);
665  ap->addrlen = addrlen;
666  ap->cstate = cstate;
667 
668  switch (ap->addr->sa_family)
669  {
670  case AF_INET:
671  ((struct sockaddr_in *) ap->addr)->sin_port = htons (cstate->port);
672  break;
673 
674  case AF_INET6:
675  ((struct sockaddr_in6 *) ap->addr)->sin6_port = htons (cstate->port);
676  break;
677 
678  default:
679  GNUNET_break (0);
680  GNUNET_free (ap);
681  return; /* not supported by us */
682  }
683  ap->sock = GNUNET_NETWORK_socket_create (ap->addr->sa_family,
684  SOCK_STREAM,
685  0);
686  if (NULL == ap->sock)
687  {
688  GNUNET_free (ap);
689  return; /* not supported by OS */
690  }
691  if ((GNUNET_OK !=
693  ap->addr,
694  ap->addrlen)) &&
695  (EINPROGRESS != errno))
696  {
697  /* maybe refused / unsupported address, try next */
699  "connect");
702  GNUNET_free (ap);
703  return;
704  }
706  cstate->ap_tail,
707  ap);
709  ap->sock,
711  ap);
712 }
713 
714 
723 static int
725  const struct GNUNET_CONFIGURATION_Handle *cfg)
726 {
727  int ret = GNUNET_SYSERR;
728  char *hostname = NULL;
729  unsigned long long port;
730 
731 #if AF_UNIX
732  char *unixpath = NULL;
733 
734  if ((GNUNET_OK ==
736  service_name,
737  "UNIXPATH",
738  &unixpath)) &&
739  (0 < strlen (unixpath)))
740  ret = GNUNET_OK;
741  else if ((GNUNET_OK ==
743  service_name,
744  "UNIXPATH")))
745  {
747  service_name,
748  "UNIXPATH",
749  _ ("not a valid filename"));
750  GNUNET_free (unixpath);
751  return GNUNET_SYSERR; /* UNIXPATH specified but invalid! */
752  }
753  GNUNET_free (unixpath);
754 #endif
755 
756  if ((GNUNET_YES ==
758  service_name,
759  "PORT")) &&
760  (GNUNET_OK ==
762  service_name,
763  "PORT",
764  &port)) &&
765  (port <= 65535) &&
766  (0 != port) &&
767  (GNUNET_OK ==
769  service_name,
770  "HOSTNAME",
771  &hostname)) &&
772  (0 != strlen (hostname)))
773  ret = GNUNET_OK;
775  return ret;
776 }
777 
778 
784 static void
785 start_connect (void *cls)
786 {
787  struct ClientState *cstate = cls;
788 
789  cstate->retry_task = NULL;
790 #if 0
791  /* Never use a local source if a proxy is configured */
792  if (GNUNET_YES ==
794  cstate->cfg))
795  {
796  socks_connect (cstate);
797  return;
798  }
799 #endif
800 
801  if ((0 == (cstate->attempts++ % 2)) ||
802  (0 == cstate->port) ||
803  (NULL == cstate->hostname))
804  {
805  /* on even rounds, try UNIX first, or always
806  if we do not have a DNS name and TCP port. */
807  cstate->sock = try_unixpath (cstate->service_name,
808  cstate->cfg);
809  if (NULL != cstate->sock)
810  {
812  return;
813  }
814  }
815  if ((NULL == cstate->hostname) ||
816  (0 == cstate->port))
817  {
818  /* All options failed. Boo! */
819  connect_fail_continuation (cstate);
820  return;
821  }
822  cstate->dns_active
823  = GNUNET_RESOLVER_ip_get (cstate->hostname,
824  AF_UNSPEC,
827  cstate);
828 }
829 
830 
838 static void
840  const struct GNUNET_MessageHeader *msg,
841  void *impl_state)
842 {
843  struct ClientState *cstate = impl_state;
844 
845  (void) mq;
846  /* only one message at a time allowed */
847  GNUNET_assert (NULL == cstate->msg);
848  GNUNET_assert (NULL == cstate->send_task);
849  cstate->msg = msg;
850  cstate->msg_off = 0;
851  if (NULL == cstate->sock)
852  {
854  "message of type %u waiting for socket\n",
855  ntohs (msg->type));
856  return; /* still waiting for connection */
857  }
858  cstate->send_task
860  cstate);
861 }
862 
863 
870 static void
872  void *impl_state)
873 {
874  struct ClientState *cstate = impl_state;
875 
876  (void) mq;
877  GNUNET_assert (NULL != cstate->msg);
878  GNUNET_assert (0 == cstate->msg_off);
879  cstate->msg = NULL;
880  if (NULL != cstate->send_task)
881  {
883  cstate->send_task = NULL;
884  }
885 }
886 
887 
900 int
902  const char *service_name)
903 {
904  char *hostname = NULL;
905  unsigned long long port;
906  int ret;
907 
908 #if AF_UNIX
909  {
910  char *unixpath = NULL;
911 
912  if (GNUNET_OK ==
914  service_name,
915  "UNIXPATH",
916  &unixpath))
917  {
918  if (0 == strlen (unixpath))
919  {
920  GNUNET_free (unixpath);
921  return GNUNET_SYSERR; /* empty string not OK */
922  }
923  if (0 == access (unixpath,
924  F_OK))
925  {
926  GNUNET_free (unixpath);
927  return GNUNET_OK; /* file exists, we assume service is running */
928  }
929  GNUNET_free (unixpath);
930  }
931  else if (GNUNET_OK ==
933  service_name,
934  "UNIXPATH"))
935  {
936  /* UNIXPATH specified but not a valid path! */
938  service_name,
939  "UNIXPATH",
940  _ ("not a valid filename"));
941  return GNUNET_SYSERR;
942  }
943  }
944 #endif
945 
946  if ( (GNUNET_OK !=
948  service_name,
949  "PORT",
950  &port)) ||
951  (port > 65535) ||
952  (0 == port) )
953  {
954  return GNUNET_SYSERR;
955  }
956  if (GNUNET_OK ==
958  service_name,
959  "HOSTNAME",
960  &hostname))
961  {
962  /* We always assume remotes are up */
963  ret = GNUNET_YES;
964  }
965  else
966  {
967  /* We look for evidence the service is up */
968  ret = GNUNET_NO;
969  }
970  if ( (NULL == hostname) ||
971  (0 == strcasecmp (hostname,
972  "localhost")) ||
973  (0 == strcasecmp (hostname,
974  "ip6-localnet")) )
975  {
976  /* service runs on loopback */
977  struct sockaddr_in v4;
978  struct sockaddr_in6 v6;
979  int sock;
980 
981  memset (&v4, 0, sizeof (v4));
982  memset (&v6, 0, sizeof (v6));
983  v4.sin_family = AF_INET;
984  v4.sin_port = htons ((uint16_t) port);
985 #if HAVE_SOCKADDR_IN_SUN_LEN
986  v4.sin_len = (u_char) sizeof(struct sockaddr_in);
987 #endif
988  inet_pton (AF_INET,
989  "127.0.0.1",
990  &v4.sin_addr);
991  ret = GNUNET_NO;
992  sock = socket (AF_INET,
993  SOCK_STREAM,
994  0);
995  if (-1 != sock)
996  {
997  if (0 != bind (sock,
998  (struct sockaddr *) &v4,
999  sizeof (v4)))
1000  {
1001  /* bind failed, so someone is listening! */
1002  ret = GNUNET_YES;
1003  }
1004  (void) close (sock);
1005  }
1006  else
1007  {
1009  "socket");
1010  if (GNUNET_NO == ret)
1011  ret = GNUNET_SYSERR;
1012  }
1013  v6.sin6_family = AF_INET6;
1014  v6.sin6_port = htons ((uint16_t) port);
1015 #if HAVE_SOCKADDR_IN_SUN_LEN
1016  v6.sin6_len = (u_char) sizeof(struct sockaddr_in6);
1017 #endif
1018  inet_pton (AF_INET6,
1019  "::1",
1020  &v6.sin6_addr);
1021  sock = socket (AF_INET6,
1022  SOCK_STREAM,
1023  0);
1024  if (-1 != sock)
1025  {
1026  if (0 != bind (sock,
1027  (struct sockaddr *) &v6,
1028  sizeof (v6)))
1029  {
1030  /* bind failed, so someone is listening! */
1031  ret = GNUNET_YES;
1032  }
1033  (void) close (sock);
1034  }
1035  else
1036  {
1038  "socket");
1039  /* not changing 'ret' intentionally here, as
1040  v4 succeeding and v6 failing just means we
1041  should use v4 */
1042  }
1043  }
1044  else
1045  {
1046  /* service running remotely */
1047  ret = GNUNET_OK;
1048  }
1050  return ret;
1051 }
1052 
1053 
1054 struct GNUNET_MQ_Handle *
1056  const char *service_name,
1057  const struct GNUNET_MQ_MessageHandler *handlers,
1059  void *error_handler_cls)
1060 {
1061  struct ClientState *cstate;
1062 
1063  if (GNUNET_OK !=
1065  cfg))
1066  return NULL;
1067  cstate = GNUNET_new (struct ClientState);
1069  cstate->cfg = cfg;
1071  cstate);
1072  cstate->mst = GNUNET_MST_create (&recv_message,
1073  cstate);
1074  if (GNUNET_YES ==
1076  service_name,
1077  "PORT"))
1078  {
1079  if (! ((GNUNET_OK !=
1081  service_name,
1082  "PORT",
1083  &cstate->port)) ||
1084  (cstate->port > 65535) ||
1085  (GNUNET_OK !=
1087  service_name,
1088  "HOSTNAME",
1089  &cstate->hostname))) &&
1090  (0 == strlen (cstate->hostname)))
1091  {
1092  GNUNET_free (cstate->hostname);
1093  cstate->hostname = NULL;
1095  _ ("Need a non-empty hostname for service `%s'.\n"),
1096  service_name);
1097  }
1098  }
1102  cstate,
1103  handlers,
1104  error_handler,
1105  error_handler_cls);
1106  return cstate->mq;
1107 }
1108 
1109 
1110 /* end of client.c */
struct GNUNET_MQ_Handle * mq
Definition: 003.c:5
struct GNUNET_MessageHeader * msg
Definition: 005.c:2
static void error_handler(void *cls, enum GNUNET_MQ_Error error)
We encountered an error handling the MQ to the ATS service.
static void try_connect_using_address(void *cls, const struct sockaddr *addr, socklen_t addrlen)
Try to establish a connection given the specified address.
Definition: client.c:636
static void connect_success_continuation(struct ClientState *cstate)
We've succeeded in establishing a connection.
Definition: client.c:481
static void connection_client_cancel_impl(struct GNUNET_MQ_Handle *mq, void *impl_state)
Cancel the currently sent message.
Definition: client.c:871
static void connection_client_send_impl(struct GNUNET_MQ_Handle *mq, const struct GNUNET_MessageHeader *msg, void *impl_state)
Implements the transmission functionality of a message queue.
Definition: client.c:839
static void start_connect(void *cls)
Try to connect to the service.
Definition: client.c:785
static void transmit_ready(void *cls)
We are ready to send a message to the service.
Definition: client.c:249
static void connect_probe_continuation(void *cls)
Scheduler let us know that we're either ready to write on the socket OR connect timed out.
Definition: client.c:581
static void receive_ready(void *cls)
This function is called once we have data ready to read.
Definition: client.c:439
static int recv_message(void *cls, const struct GNUNET_MessageHeader *msg)
We have received a full message, pass to the MQ dispatcher.
Definition: client.c:334
static struct GNUNET_NETWORK_Handle * try_unixpath(const char *service_name, const struct GNUNET_CONFIGURATION_Handle *cfg)
Try connecting to the server using UNIX domain sockets.
Definition: client.c:509
static void connection_client_destroy_impl(struct GNUNET_MQ_Handle *mq, void *impl_state)
Implement the destruction of a message queue.
Definition: client.c:385
static void cancel_aps(struct ClientState *cstate)
Cancel all remaining connect attempts.
Definition: client.c:360
static void connect_fail_continuation(struct ClientState *cstate)
We've failed for good to establish a connection (timeout or no more addresses to try).
Definition: client.c:220
static int test_service_configuration(const char *service_name, const struct GNUNET_CONFIGURATION_Handle *cfg)
Test whether the configuration has proper values for connection (UNIXPATH || (PORT && HOSTNAME)).
Definition: client.c:724
#define LOG(kind,...)
Definition: client.c:36
#define CONNECT_RETRY_TIMEOUT
Timeout we use on TCP connect before trying another result from the DNS resolver.
Definition: client.c:44
static const struct GNUNET_CONFIGURATION_Handle * cfg
Configuration we are using.
Definition: gnunet-abd.c:36
static int ret
Return value of the commandline.
Definition: gnunet-abd.c:81
static uint16_t port
Port number.
Definition: gnunet-bcd.c:147
static struct GNUNET_CADET_MessageHandler handlers[]
Handlers, for diverse services.
uint16_t len
length of data (which is always a uint32_t, but presumably this can be used to specify that fewer byt...
static char * hostname
Our hostname; we give this to all the peers we start.
static char * service_name
Option -s: service name (hash to get service descriptor)
Definition: gnunet-vpn.c:51
Constants for network protocols.
int GNUNET_CLIENT_test(const struct GNUNET_CONFIGURATION_Handle *cfg, const char *service_name)
Test if the port or UNIXPATH of the given service_name is in use and thus (most likely) the respectiv...
Definition: client.c:901
struct GNUNET_MQ_Handle * GNUNET_CLIENT_connect(const struct GNUNET_CONFIGURATION_Handle *cfg, const char *service_name, const struct GNUNET_MQ_MessageHandler *handlers, GNUNET_MQ_ErrorHandler error_handler, void *error_handler_cls)
Create a message queue to connect to a GNUnet service.
Definition: client.c:1055
enum GNUNET_GenericReturnValue GNUNET_CONFIGURATION_get_value_filename(const struct GNUNET_CONFIGURATION_Handle *cfg, const char *section, const char *option, char **value)
Get a configuration value that should be the name of a file or directory.
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.
#define GNUNET_CONTAINER_DLL_remove(head, tail, element)
Remove an element from a DLL.
#define GNUNET_CONTAINER_DLL_insert(head, tail, element)
Insert an element at the head of a DLL.
#define GNUNET_memcpy(dst, src, n)
Call memcpy() but check for n being 0 first.
@ GNUNET_OK
Definition: gnunet_common.h:99
@ GNUNET_YES
@ GNUNET_NO
Definition: gnunet_common.h:98
@ GNUNET_SYSERR
Definition: gnunet_common.h:97
#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.
void GNUNET_log_config_invalid(enum GNUNET_ErrorType kind, const char *section, const char *option, const char *required)
Log error message about invalid configuration option value.
#define GNUNET_log_strerror(level, cmd)
Log an error message at log-level 'level' that indicates a failure of the command 'cmd' with the mess...
const char * GNUNET_a2s(const struct sockaddr *addr, socklen_t addrlen)
Convert a "struct sockaddr*" (IPv4 or IPv6 address) to a string (for printing debug messages).
@ GNUNET_ERROR_TYPE_WARNING
@ GNUNET_ERROR_TYPE_ERROR
@ GNUNET_ERROR_TYPE_DEBUG
@ GNUNET_ERROR_TYPE_INFO
#define GNUNET_strdup(a)
Wrapper around GNUNET_xstrdup_.
#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_inject_error(struct GNUNET_MQ_Handle *mq, enum GNUNET_MQ_Error error)
Call the error handler of a message queue with the given error code.
Definition: mq.c:267
void(* GNUNET_MQ_ErrorHandler)(void *cls, enum GNUNET_MQ_Error error)
Generic error handler, called with the appropriate error code and the same closure specified at the c...
struct GNUNET_MQ_Handle * GNUNET_MQ_queue_for_callbacks(GNUNET_MQ_SendImpl send, GNUNET_MQ_DestroyImpl destroy, GNUNET_MQ_CancelImpl cancel, void *impl_state, const struct GNUNET_MQ_MessageHandler *handlers, GNUNET_MQ_ErrorHandler error_handler, void *cls)
Create a message queue for the specified handlers.
Definition: mq.c:467
void GNUNET_MQ_impl_send_continue(struct GNUNET_MQ_Handle *mq)
Call the send implementation for the next queued message, if any.
Definition: mq.c:423
void GNUNET_MQ_inject_message(struct GNUNET_MQ_Handle *mq, const struct GNUNET_MessageHeader *mh)
Call the message message handler that was registered for the type of the given message in the given m...
Definition: mq.c:186
void GNUNET_MQ_impl_send_in_flight(struct GNUNET_MQ_Handle *mq)
Call the send notification for the current message, but do not try to send the next message until #gn...
Definition: mq.c:446
@ GNUNET_MQ_ERROR_READ
Failed to read message from the network.
@ GNUNET_MQ_ERROR_WRITE
FIXME: document!
enum GNUNET_GenericReturnValue GNUNET_NETWORK_socket_getsockopt(const struct GNUNET_NETWORK_Handle *desc, int level, int optname, void *optval, socklen_t *optlen)
Get socket options.
Definition: network.c:631
enum GNUNET_GenericReturnValue GNUNET_NETWORK_socket_close(struct GNUNET_NETWORK_Handle *desc)
Close a socket.
Definition: network.c:508
enum GNUNET_GenericReturnValue GNUNET_NETWORK_socket_connect(const struct GNUNET_NETWORK_Handle *desc, const struct sockaddr *address, socklen_t address_len)
Connect a socket to some remote address.
Definition: network.c:606
struct GNUNET_NETWORK_Handle * GNUNET_NETWORK_socket_create(int domain, int type, int protocol)
Create a new socket.
Definition: network.c:855
char * GNUNET_NETWORK_shorten_unixpath(char *unixpath)
Given a unixpath that is too long (larger than UNIX_PATH_MAX), shorten it to an acceptable length whi...
Definition: network.c:143
ssize_t GNUNET_NETWORK_socket_send(const struct GNUNET_NETWORK_Handle *desc, const void *buffer, size_t length)
Send data (always non-blocking).
Definition: network.c:760
void GNUNET_RESOLVER_request_cancel(struct GNUNET_RESOLVER_RequestHandle *rh)
Cancel a request that is still pending with the resolver.
struct GNUNET_RESOLVER_RequestHandle * GNUNET_RESOLVER_ip_get(const char *hostname, int af, struct GNUNET_TIME_Relative timeout, GNUNET_RESOLVER_AddressCallback callback, void *callback_cls)
Convert a string to one or more IP addresses.
Definition: resolver_api.c:939
struct GNUNET_SCHEDULER_Task * GNUNET_SCHEDULER_add_now(GNUNET_SCHEDULER_TaskCallback task, void *task_cls)
Schedule a new task to be run as soon as possible.
Definition: scheduler.c:1281
struct GNUNET_SCHEDULER_Task * GNUNET_SCHEDULER_add_write_net(struct GNUNET_TIME_Relative delay, struct GNUNET_NETWORK_Handle *wfd, GNUNET_SCHEDULER_TaskCallback task, void *task_cls)
Schedule a new task to be run with a specified delay or when the specified file descriptor is ready f...
Definition: scheduler.c:1573
struct GNUNET_SCHEDULER_Task * GNUNET_SCHEDULER_add_read_net(struct GNUNET_TIME_Relative delay, struct GNUNET_NETWORK_Handle *rfd, GNUNET_SCHEDULER_TaskCallback task, void *task_cls)
Schedule a new task to be run with a specified delay or when the specified file descriptor is ready f...
Definition: scheduler.c:1502
const struct GNUNET_SCHEDULER_TaskContext * GNUNET_SCHEDULER_get_task_context(void)
Obtain the reasoning why the current task was started.
Definition: scheduler.c:737
void * GNUNET_SCHEDULER_cancel(struct GNUNET_SCHEDULER_Task *task)
Cancel the task with the specified identifier.
Definition: scheduler.c:957
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:1254
@ GNUNET_SCHEDULER_REASON_WRITE_READY
The writing socket is ready.
int GNUNET_MST_read(struct GNUNET_MessageStreamTokenizer *mst, struct GNUNET_NETWORK_Handle *sock, int purge, int one_shot)
Add incoming data to the receive buffer and call the callback for all complete messages.
Definition: mst.c:352
void GNUNET_MST_destroy(struct GNUNET_MessageStreamTokenizer *mst)
Destroys a tokenizer.
Definition: mst.c:418
struct GNUNET_MessageStreamTokenizer * GNUNET_MST_create(GNUNET_MessageTokenizerCallback cb, void *cb_cls)
Create a message stream tokenizer.
Definition: mst.c:85
int GNUNET_SOCKS_check_service(const char *service_name, const struct GNUNET_CONFIGURATION_Handle *cfg)
Check if a SOCKS proxy is required by a service.
Definition: socks.c:593
size_t GNUNET_strlcpy(char *dst, const char *src, size_t n)
Like strlcpy but portable.
Definition: strings.c:139
#define GNUNET_TIME_UNIT_FOREVER_REL
Constant used to specify "forever".
const char * GNUNET_STRINGS_relative_time_to_string(struct GNUNET_TIME_Relative delta, int do_round)
Give relative time in human-readable fancy format.
Definition: strings.c:570
#define GNUNET_TIME_STD_BACKOFF(r)
Perform our standard exponential back-off calculation, starting at 1 ms and then going by a factor of...
#define _(String)
GNU gettext support macro.
Definition: platform.h:177
#define RETRY
Return code we give on 'send' if we failed to send right now but it makes sense to retry later.
static struct GNUNET_SCHEDULER_TaskContext tc
Task context of the current task.
Definition: scheduler.c:423
During connect, we try multiple possible IP addresses to find out which one might work.
socklen_t addrlen
Length of addr.
struct AddressProbe * prev
This is a doubly-linked list.
struct GNUNET_SCHEDULER_Task * task
Task waiting for the connection to finish connecting.
struct GNUNET_NETWORK_Handle * sock
Underlying OS's socket.
struct ClientState * cstate
Connection for which we are probing.
Definition: client.c:83
const struct sockaddr * addr
The address; do not free (allocated at the end of this struct).
struct AddressProbe * next
This is a linked list.
State we keep per client.
struct GNUNET_MQ_Handle * mq
MQ to talk to client.
const struct GNUNET_CONFIGURATION_Handle * cfg
Our configuration.
Definition: client.c:115
struct GNUNET_MessageStreamTokenizer * mst
Tokenizer for inbound messages.
Definition: client.c:162
int in_destroy
Are we supposed to die? GNUNET_SYSERR if destruction must be deferred, GNUNET_NO by default,...
Definition: client.c:200
unsigned int attempts
How often have we tried to connect?
Definition: client.c:193
const struct GNUNET_MessageHeader * msg
Next message to transmit to the service.
Definition: client.c:142
size_t msg_off
Offset in the message where we are for transmission.
Definition: client.c:188
struct GNUNET_SCHEDULER_Task * retry_task
Task for trying to connect to the service.
Definition: client.c:147
struct GNUNET_TIME_Relative back_off
Current value for our incremental back-off (for connect re-tries).
Definition: client.c:178
struct GNUNET_SCHEDULER_Task * send_task
Task for sending messages to the service.
Definition: client.c:152
char * hostname
Hostname, if any.
Definition: client.c:137
struct GNUNET_RESOLVER_RequestHandle * dns_active
Handle to a pending DNS lookup request, NULL if DNS is finished.
Definition: client.c:110
unsigned long long port
TCP port (0 for disabled).
Definition: client.c:183
struct GNUNET_TIME_Absolute receive_timeout
Timeout for receiving a response (absolute time).
Definition: client.c:172
struct GNUNET_SCHEDULER_Task * recv_task
Task for sending messages to the service.
Definition: client.c:157
struct GNUNET_NETWORK_Handle * sock
The connection handle, NULL if not live.
Definition: client.c:105
char * service_name
Name of the service we interact with.
Definition: client.c:132
struct AddressProbe * ap_tail
Linked list of sockets we are currently trying out (during connect).
Definition: client.c:127
struct AddressProbe * ap_head
Linked list of sockets we are currently trying out (during connect).
Definition: client.c:121
Handle to a message queue.
Definition: mq.c:86
void * error_handler_cls
Closure for the error handler.
Definition: mq.c:121
Message handler for a specific message type.
Header for all communications.
uint16_t type
The type of the message (GNUNET_MESSAGE_TYPE_XXXX), in big-endian format.
uint16_t size
The length of the struct (in bytes, including the length field itself), in big-endian format.
Handle to a message stream tokenizer.
Definition: mst.c:44
handle to a socket
Definition: network.c:53
Handle to a request given to the resolver.
Definition: resolver_api.c:103
Context information passed to each scheduler task.
enum GNUNET_SCHEDULER_Reason reason
Reason why the task is run now.
Entry in list of pending tasks.
Definition: scheduler.c:135
Time for absolute times used by GNUnet, in microseconds.
Time for relative time used by GNUnet, in microseconds.