GNUnet  0.10.x
gnunet-service-identity.c
Go to the documentation of this file.
1 /*
2  This file is part of GNUnet.
3  Copyright (C) 2013 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 
33 #include "platform.h"
34 #include "gnunet_util_lib.h"
35 #include "gnunet_constants.h"
36 #include "gnunet_protocols.h"
39 #include "identity.h"
40 
41 
45 struct Ego
46 {
47 
51  struct Ego *next;
52 
56  struct Ego *prev;
57 
62 
66  char *identifier;
67 
68 };
69 
70 
74 static const struct GNUNET_CONFIGURATION_Handle *cfg;
75 
81 
86 
91 
95 static char *ego_directory;
96 
100 static char *subsystem_cfg_file;
101 
105 static struct Ego *ego_head;
106 
110 static struct Ego *ego_tail;
111 
112 
119 static char *
120 get_ego_filename (struct Ego *ego)
121 {
122  char *filename;
123 
124  GNUNET_asprintf (&filename,
125  "%s%s%s",
128  ego->identifier);
129  return filename;
130 }
131 
139 static void
141  struct GNUNET_SERVICE_Client *client,
142  void *app_ctx)
143 {
145  "Client %p disconnected\n",
146  client);
147 }
148 
149 
158 static void *
159 client_connect_cb (void *cls,
160  struct GNUNET_SERVICE_Client *client,
161  struct GNUNET_MQ_Handle *mq)
162 {
163  return client;
164 }
165 
171 static void
172 shutdown_task (void *cls)
173 {
174  struct Ego *e;
175 
176  if (NULL != nc)
177  {
179  nc = NULL;
180  }
181  if (NULL != stats)
182  {
184  stats = NULL;
185  }
186  GNUNET_CONFIGURATION_destroy (subsystem_cfg);
187  subsystem_cfg = NULL;
189  subsystem_cfg_file = NULL;
191  ego_directory = NULL;
192  while (NULL != (e = ego_head))
193  {
194  GNUNET_CONTAINER_DLL_remove (ego_head, ego_tail, e);
195  GNUNET_free (e->pk);
196  GNUNET_free (e->identifier);
197  GNUNET_free (e);
198  }
199 }
200 
201 
209 static void
211  uint32_t result_code,
212  const char *emsg)
213 {
214  struct ResultCodeMessage *rcm;
215  struct GNUNET_MQ_Envelope *env;
216  size_t elen;
217 
218  if (NULL == emsg)
219  elen = 0;
220  else
221  elen = strlen (emsg) + 1;
222  env = GNUNET_MQ_msg_extra (rcm,
223  elen,
225  rcm->result_code = htonl (result_code);
226  if (0 < elen)
227  GNUNET_memcpy (&rcm[1], emsg, elen);
229  "Sending result %d (%s) to client\n",
230  (int) result_code,
231  emsg);
233 }
234 
235 
242 static struct GNUNET_MQ_Envelope *
244 {
245  struct UpdateMessage *um;
246  struct GNUNET_MQ_Envelope *env;
247  size_t name_len;
248 
249  name_len = (NULL == ego->identifier) ? 0 : (strlen (ego->identifier) + 1);
250  env = GNUNET_MQ_msg_extra (um,
251  name_len,
253  um->name_len = htons (name_len);
254  um->end_of_list = htons (GNUNET_NO);
255  um->private_key = *ego->pk;
256  GNUNET_memcpy (&um[1], ego->identifier, name_len);
257  return env;
258 }
259 
260 
268 static struct GNUNET_MQ_Envelope *
270  const char *servicename)
271 {
272  struct SetDefaultMessage *sdm;
273  struct GNUNET_MQ_Envelope *env;
274  size_t name_len;
275 
276  name_len = (NULL == servicename) ? 0 : (strlen (servicename) + 1);
277  env = GNUNET_MQ_msg_extra (sdm,
278  name_len,
280  sdm->name_len = htons (name_len);
281  sdm->reserved = htons (0);
282  sdm->private_key = *ego->pk;
283  GNUNET_memcpy (&sdm[1], servicename, name_len);
284  return env;
285 }
286 
287 
297 static void
299  const struct GNUNET_MessageHeader *message)
300 {
301  struct GNUNET_SERVICE_Client *client = cls;
302  struct UpdateMessage *ume;
303  struct GNUNET_MQ_Envelope *env;
304  struct Ego *ego;
305 
307  "Received START message from client\n");
312  for (ego = ego_head; NULL != ego; ego = ego->next)
313  {
314  env = create_update_message (ego);
316  }
317  env = GNUNET_MQ_msg_extra (ume,
318  0,
320  ume->end_of_list = htons (GNUNET_YES);
321  ume->name_len = htons (0);
324 }
325 
326 
335 static int
337  const struct LookupMessage *message)
338 {
340  return GNUNET_OK;
341 }
342 
343 
351 static void
353  const struct LookupMessage *message)
354 {
355  struct GNUNET_SERVICE_Client *client = cls;
356  const char *name;
357  struct GNUNET_MQ_Envelope *env;
358  struct Ego *ego;
359 
361  "Received LOOKUP message from client\n");
362  name = (const char *) &message[1];
363  for (ego = ego_head; NULL != ego; ego = ego->next)
364  {
365  if (0 != strcasecmp (name,
366  ego->identifier))
367  continue;
368  env = create_update_message (ego);
371  return;
372  }
373  send_result_code (client,
374  0,
375  "ego not found");
377 }
378 
379 
388 static int
390  const struct LookupMessage *message)
391 {
393  return GNUNET_OK;
394 }
395 
396 
404 static void
406  const struct LookupMessage *message)
407 {
408  struct GNUNET_SERVICE_Client *client = cls;
409  const char *name;
410  struct GNUNET_MQ_Envelope *env;
411  struct Ego *lprefix;
412 
414  "Received LOOKUP_BY_SUFFIX message from client\n");
415  name = (const char *) &message[1];
416  lprefix = NULL;
417  for (struct Ego *ego = ego_head; NULL != ego; ego = ego->next)
418  {
419 
420  if ((strlen (ego->identifier) <= strlen (name)) &&
421  (0 == strcmp (ego->identifier,
422  &name[strlen (name) - strlen (ego->identifier)])) &&
423  ((strlen (name) == strlen (ego->identifier)) ||
424  ('.' == name[strlen (name) -
425  strlen (ego->identifier) - 1])) &&
426  ((NULL == lprefix) ||
427  (strlen (ego->identifier) > strlen (lprefix->identifier))))
428  {
429  /* found better match, update! */
430  lprefix = ego;
431  }
432  }
433  if (NULL != lprefix)
434  {
435  env = create_update_message (lprefix);
438  return;
439  }
440  send_result_code (client,
441  0,
442  "ego not found");
444 }
445 
446 
454 static int
456  const struct GetDefaultMessage *msg)
457 {
458  uint16_t size;
459  uint16_t name_len;
460  const char *name;
461 
462  size = ntohs (msg->header.size);
463  if (size <= sizeof (struct GetDefaultMessage))
464  {
465  GNUNET_break (0);
466  return GNUNET_SYSERR;
467  }
468  name = (const char *) &msg[1];
469  name_len = ntohs (msg->name_len);
470  if ( (name_len + sizeof (struct GetDefaultMessage) != size) ||
471  (0 != ntohs (msg->reserved)) ||
472  ('\0' != name[name_len - 1]) )
473  {
474  GNUNET_break (0);
475  return GNUNET_SYSERR;
476  }
477  return GNUNET_OK;
478 }
479 
480 
489 static void
491  const struct GetDefaultMessage *gdm)
492 {
493  struct GNUNET_MQ_Envelope *env;
494  struct GNUNET_SERVICE_Client *client = cls;
495  struct Ego *ego;
496  char *name;
497  char *identifier;
498 
499 
500  name = GNUNET_strdup ((const char *) &gdm[1]);
501  GNUNET_STRINGS_utf8_tolower ((const char *) &gdm[1], name);
503  "Received GET_DEFAULT for service `%s' from client\n",
504  name);
505  if (GNUNET_OK !=
507  name,
508  "DEFAULT_IDENTIFIER",
509  &identifier))
510  {
511  send_result_code (client, 1, gettext_noop ("no default known"));
513  GNUNET_free (name);
514  return;
515  }
516  for (ego = ego_head; NULL != ego; ego = ego->next)
517  {
518  if (0 == strcmp (ego->identifier,
519  identifier))
520  {
521  env = create_set_default_message (ego,
522  name);
525  GNUNET_free (identifier);
526  GNUNET_free (name);
527  return;
528  }
529  }
530  GNUNET_free (identifier);
532  "Failed to find ego `%s'\n",
533  name);
534  GNUNET_free (name);
535  send_result_code (client, 1,
536  gettext_noop ("default configured, but ego unknown (internal error)"));
538 }
539 
540 
548 static int
550  const struct GNUNET_CRYPTO_EcdsaPrivateKey *pk2)
551 {
552  return GNUNET_memcmp (pk1, pk2);
553 }
554 
562 static int
564  const struct SetDefaultMessage *msg)
565 {
566  uint16_t size;
567  uint16_t name_len;
568  const char *str;
569 
570  size = ntohs (msg->header.size);
571  if (size <= sizeof (struct SetDefaultMessage))
572  {
573  GNUNET_break (0);
574  return GNUNET_SYSERR;
575  }
576  name_len = ntohs (msg->name_len);
577  GNUNET_break (0 == ntohs (msg->reserved));
578  if (name_len + sizeof (struct SetDefaultMessage) != size)
579  {
580  GNUNET_break (0);
581  return GNUNET_SYSERR;
582  }
583  str = (const char *) &msg[1];
584  if ('\0' != str[name_len - 1])
585  {
586  GNUNET_break (0);
587  return GNUNET_SYSERR;
588  }
589  return GNUNET_OK;
590 }
591 
600 static void
602  const struct SetDefaultMessage *sdm)
603 {
604  struct Ego *ego;
605  struct GNUNET_SERVICE_Client *client = cls;
606  char *str;
607 
608  str = GNUNET_strdup ((const char *) &sdm[1]);
609  GNUNET_STRINGS_utf8_tolower ((const char *) &sdm[1], str);
610 
612  "Received SET_DEFAULT for service `%s' from client\n",
613  str);
614  for (ego = ego_head; NULL != ego; ego = ego->next)
615  {
616  if (0 == key_cmp (ego->pk,
617  &sdm->private_key))
618  {
620  str,
621  "DEFAULT_IDENTIFIER",
622  ego->identifier);
623  if (GNUNET_OK !=
624  GNUNET_CONFIGURATION_write (subsystem_cfg,
627  _("Failed to write subsystem default identifier map to `%s'.\n"),
629  send_result_code (client, 0, NULL);
631  GNUNET_free (str);
632  return;
633  }
634  }
635  send_result_code (client, 1, _("Unknown ego specified for service (internal error)"));
636  GNUNET_free (str);
638 }
639 
640 
646 static void
647 notify_listeners (struct Ego *ego)
648 {
649  struct UpdateMessage *um;
650  size_t name_len;
651 
652  name_len = (NULL == ego->identifier) ? 0 : (strlen (ego->identifier) + 1);
653  um = GNUNET_malloc (sizeof (struct UpdateMessage) + name_len);
655  um->header.size = htons (sizeof (struct UpdateMessage) + name_len);
656  um->name_len = htons (name_len);
657  um->end_of_list = htons (GNUNET_NO);
658  um->private_key = *ego->pk;
659  GNUNET_memcpy (&um[1], ego->identifier, name_len);
661  &um->header,
662  GNUNET_NO);
663  GNUNET_free (um);
664 }
665 
673 static int
675  const struct CreateRequestMessage *msg)
676 {
677 
678  uint16_t size;
679  uint16_t name_len;
680  const char *str;
681 
682  size = ntohs (msg->header.size);
683  if (size <= sizeof (struct CreateRequestMessage))
684  {
685  GNUNET_break (0);
686  return GNUNET_SYSERR;
687  }
688  name_len = ntohs (msg->name_len);
689  GNUNET_break (0 == ntohs (msg->reserved));
690  if (name_len + sizeof (struct CreateRequestMessage) != size)
691  {
692  GNUNET_break (0);
693  return GNUNET_SYSERR;
694  }
695  str = (const char *) &msg[1];
696  if ('\0' != str[name_len - 1])
697  {
698  GNUNET_break (0);
699  return GNUNET_SYSERR;
700  }
701  return GNUNET_OK;
702 }
703 
712 static void
714  const struct CreateRequestMessage *crm)
715 {
716  struct GNUNET_SERVICE_Client *client = cls;
717  struct Ego *ego;
718  char *str;
719  char *fn;
720 
722  "Received CREATE message from client\n");
723  str = GNUNET_strdup ((const char *) &crm[1]);
724  GNUNET_STRINGS_utf8_tolower ((const char *) &crm[1], str);
725  for (ego = ego_head; NULL != ego; ego = ego->next)
726  {
727  if (0 == strcmp (ego->identifier,
728  str))
729  {
730  send_result_code (client, 1, gettext_noop ("identifier already in use for another ego"));
732  GNUNET_free (str);
733  return;
734  }
735  }
736  ego = GNUNET_new (struct Ego);
738  *ego->pk = crm->private_key;
739  ego->identifier = GNUNET_strdup (str);
740  GNUNET_CONTAINER_DLL_insert (ego_head,
741  ego_tail,
742  ego);
743  send_result_code (client, 0, NULL);
744  fn = get_ego_filename (ego);
746  if (sizeof (struct GNUNET_CRYPTO_EcdsaPrivateKey) !=
748  &crm->private_key,
749  sizeof (struct GNUNET_CRYPTO_EcdsaPrivateKey),
753  "write", fn);
754  GNUNET_free (fn);
755  GNUNET_free (str);
756  notify_listeners (ego);
758 }
759 
760 
765 {
769  const char *old_name;
770 
774  const char *new_name;
775 };
776 
784 static void
785 handle_ego_rename (void *cls,
786  const char *section)
787 {
788  struct RenameContext *rc = cls;
789  char *id;
790 
791  if (GNUNET_OK !=
793  section,
794  "DEFAULT_IDENTIFIER",
795  &id))
796  return;
797  if (0 != strcmp (id, rc->old_name))
798  {
799  GNUNET_free (id);
800  return;
801  }
803  section,
804  "DEFAULT_IDENTIFIER",
805  rc->new_name);
806  GNUNET_free (id);
807 }
808 
816 static int
818  const struct RenameMessage *msg)
819 {
820  uint16_t size;
821  uint16_t old_name_len;
822  uint16_t new_name_len;
823  const char *old_name;
824  const char *new_name;
825 
826  size = ntohs (msg->header.size);
827  if (size <= sizeof (struct RenameMessage))
828  {
829  GNUNET_break (0);
830  return GNUNET_SYSERR;
831  }
832  old_name_len = ntohs (msg->old_name_len);
833  new_name_len = ntohs (msg->new_name_len);
834  old_name = (const char *) &msg[1];
835  new_name = &old_name[old_name_len];
836  if ( (old_name_len + new_name_len + sizeof (struct RenameMessage) != size) ||
837  ('\0' != old_name[old_name_len - 1]) ||
838  ('\0' != new_name[new_name_len - 1]) )
839  {
840  GNUNET_break (0);
841  return GNUNET_SYSERR;
842  }
843 
844  return GNUNET_OK;
845 }
846 
847 
856 static void
858  const struct RenameMessage *rm)
859 {
860  uint16_t old_name_len;
861  struct Ego *ego;
862  char *old_name;
863  char *new_name;
864  struct RenameContext rename_ctx;
865  struct GNUNET_SERVICE_Client *client = cls;
866  char *fn_old;
867  char *fn_new;
868  const char *old_name_tmp;
869 
871  "Received RENAME message from client\n");
872  old_name_len = ntohs (rm->old_name_len);
873  old_name_tmp = (const char *) &rm[1];
874  old_name = GNUNET_strdup (old_name_tmp);
875  GNUNET_STRINGS_utf8_tolower (old_name_tmp, old_name);
876  new_name = GNUNET_strdup (&old_name_tmp[old_name_len]);
877  GNUNET_STRINGS_utf8_tolower (&old_name_tmp[old_name_len], new_name);
878 
879  /* check if new name is already in use */
880  for (ego = ego_head; NULL != ego; ego = ego->next)
881  {
882  if (0 == strcmp (ego->identifier,
883  new_name))
884  {
885  send_result_code (client, 1, gettext_noop ("target name already exists"));
887  GNUNET_free (old_name);
888  GNUNET_free (new_name);
889  return;
890  }
891  }
892 
893  /* locate old name and, if found, perform rename */
894  for (ego = ego_head; NULL != ego; ego = ego->next)
895  {
896  if (0 == strcmp (ego->identifier,
897  old_name))
898  {
899  fn_old = get_ego_filename (ego);
900  GNUNET_free (ego->identifier);
901  rename_ctx.old_name = old_name;
902  rename_ctx.new_name = new_name;
905  &rename_ctx);
906  if (GNUNET_OK !=
907  GNUNET_CONFIGURATION_write (subsystem_cfg,
910  _("Failed to write subsystem default identifier map to `%s'.\n"),
912  ego->identifier = GNUNET_strdup (new_name);
913  fn_new = get_ego_filename (ego);
914  if (0 != RENAME (fn_old, fn_new))
916  GNUNET_free (fn_old);
917  GNUNET_free (fn_new);
918  GNUNET_free (old_name);
919  GNUNET_free (new_name);
920  notify_listeners (ego);
921  send_result_code (client, 0, NULL);
923  return;
924  }
925  }
926 
927  /* failed to locate old name */
928  send_result_code (client, 1, gettext_noop ("no matching ego found"));
929  GNUNET_free (old_name);
930  GNUNET_free (new_name);
932 }
933 
934 
942 static void
943 handle_ego_delete (void *cls,
944  const char *section)
945 {
946  const char *identifier = cls;
947  char *id;
948 
949  if (GNUNET_OK !=
951  section,
952  "DEFAULT_IDENTIFIER",
953  &id))
954  return;
955  if (0 != strcmp (id, identifier))
956  {
957  GNUNET_free (id);
958  return;
959  }
961  section,
962  "DEFAULT_IDENTIFIER",
963  NULL);
964  GNUNET_free (id);
965 }
966 
974 static int
976  const struct DeleteMessage *msg)
977 {
978  uint16_t size;
979  uint16_t name_len;
980  const char *name;
981 
982  size = ntohs (msg->header.size);
983  if (size <= sizeof (struct DeleteMessage))
984  {
985  GNUNET_break (0);
986  return GNUNET_SYSERR;
987  }
988  name = (const char *) &msg[1];
989  name_len = ntohs (msg->name_len);
990  if ( (name_len + sizeof (struct DeleteMessage) != size) ||
991  (0 != ntohs (msg->reserved)) ||
992  ('\0' != name[name_len - 1]) )
993  {
994  GNUNET_break (0);
995  return GNUNET_SYSERR;
996  }
997  return GNUNET_OK;
998 }
999 
1000 
1009 static void
1011  const struct DeleteMessage *dm)
1012 {
1013  struct Ego *ego;
1014  char *name;
1015  char *fn;
1016  struct GNUNET_SERVICE_Client *client = cls;
1017 
1019  "Received DELETE message from client\n");
1020  name = GNUNET_strdup ((const char *) &dm[1]);
1021  GNUNET_STRINGS_utf8_tolower ((const char *) &dm[1], name);
1022 
1023  for (ego = ego_head; NULL != ego; ego = ego->next)
1024  {
1025  if (0 == strcmp (ego->identifier,
1026  name))
1027  {
1028  GNUNET_CONTAINER_DLL_remove (ego_head,
1029  ego_tail,
1030  ego);
1033  ego->identifier);
1034  if (GNUNET_OK !=
1035  GNUNET_CONFIGURATION_write (subsystem_cfg,
1038  _("Failed to write subsystem default identifier map to `%s'.\n"),
1040  fn = get_ego_filename (ego);
1041  if (0 != UNLINK (fn))
1043  GNUNET_free (fn);
1044  GNUNET_free (ego->identifier);
1045  ego->identifier = NULL;
1046  notify_listeners (ego);
1047  GNUNET_free (ego->pk);
1048  GNUNET_free (ego);
1049  GNUNET_free (name);
1050  send_result_code (client, 0, NULL);
1052  return;
1053  }
1054  }
1055 
1056  send_result_code (client, 1, gettext_noop ("no matching ego found"));
1057  GNUNET_free (name);
1059 }
1060 
1061 
1072 static int
1073 process_ego_file (void *cls,
1074  const char *filename)
1075 {
1076  struct Ego *ego;
1077  const char *fn;
1078 
1079  fn = strrchr (filename, (int) DIR_SEPARATOR);
1080  if (NULL == fn)
1081  {
1082  GNUNET_break (0);
1083  return GNUNET_OK;
1084  }
1085  ego = GNUNET_new (struct Ego);
1086  ego->pk = GNUNET_CRYPTO_ecdsa_key_create_from_file (filename);
1087  if (NULL == ego->pk)
1088  {
1089  GNUNET_free (ego);
1091  _("Failed to parse ego information in `%s'\n"),
1092  filename);
1093  return GNUNET_OK;
1094  }
1096  "Loaded ego `%s'\n",
1097  fn + 1);
1098  ego->identifier = GNUNET_strdup (fn + 1);
1099  GNUNET_CONTAINER_DLL_insert (ego_head,
1100  ego_tail,
1101  ego);
1102  return GNUNET_OK;
1103 }
1104 
1105 
1113 static void
1114 run (void *cls,
1115  const struct GNUNET_CONFIGURATION_Handle *c,
1117 {
1118  cfg = c;
1120  if (GNUNET_OK !=
1121  GNUNET_CONFIGURATION_get_value_filename (cfg, "identity",
1122  "EGODIR",
1123  &ego_directory))
1124  {
1125  GNUNET_log_config_missing (GNUNET_ERROR_TYPE_ERROR, "identity", "EGODIR");
1127  return;
1128  }
1129  if (GNUNET_OK !=
1130  GNUNET_CONFIGURATION_get_value_filename (cfg, "identity",
1131  "SUBSYSTEM_CFG",
1133  {
1134  GNUNET_log_config_missing (GNUNET_ERROR_TYPE_ERROR, "identity", "SUBSYSTEM_CFG");
1136  return;
1137  }
1139  "Loading subsystem configuration `%s'\n",
1141  subsystem_cfg = GNUNET_CONFIGURATION_create ();
1142  if ( (GNUNET_YES ==
1144  (GNUNET_OK !=
1145  GNUNET_CONFIGURATION_parse (subsystem_cfg,
1146  subsystem_cfg_file)) )
1147  {
1149  _("Failed to parse subsystem identity configuration file `%s'\n"),
1152  return;
1153  }
1154  stats = GNUNET_STATISTICS_create ("identity", cfg);
1155  if (GNUNET_OK !=
1157  {
1159  _("Failed to create directory `%s' for storing egos\n"),
1160  ego_directory);
1161  }
1164  NULL);
1166  NULL);
1167 }
1168 
1169 
1174 ("identity",
1176  &run,
1179  NULL,
1180  GNUNET_MQ_hd_fixed_size (start_message,
1182  struct GNUNET_MessageHeader,
1183  NULL),
1184  GNUNET_MQ_hd_var_size (lookup_message,
1186  struct LookupMessage,
1187  NULL),
1188  GNUNET_MQ_hd_var_size (lookup_by_suffix_message,
1190  struct LookupMessage,
1191  NULL),
1192  GNUNET_MQ_hd_var_size (get_default_message,
1194  struct GetDefaultMessage,
1195  NULL),
1196  GNUNET_MQ_hd_var_size (set_default_message,
1198  struct SetDefaultMessage,
1199  NULL),
1200  GNUNET_MQ_hd_var_size (create_message,
1202  struct CreateRequestMessage,
1203  NULL),
1204  GNUNET_MQ_hd_var_size (rename_message,
1206  struct RenameMessage,
1207  NULL),
1208  GNUNET_MQ_hd_var_size (delete_message,
1210  struct DeleteMessage,
1211  NULL),
1213 
1214 
1215 
1216 /* end of gnunet-service-identity.c */
#define GNUNET_CONTAINER_DLL_remove(head, tail, element)
Remove an element from a DLL.
GNUNET_SERVICE_MAIN("identity", GNUNET_SERVICE_OPTION_NONE, &run, &client_connect_cb, &client_disconnect_cb, NULL, GNUNET_MQ_hd_fixed_size(start_message, GNUNET_MESSAGE_TYPE_IDENTITY_START, struct GNUNET_MessageHeader, NULL), GNUNET_MQ_hd_var_size(lookup_message, GNUNET_MESSAGE_TYPE_IDENTITY_LOOKUP, struct LookupMessage, NULL), GNUNET_MQ_hd_var_size(lookup_by_suffix_message, GNUNET_MESSAGE_TYPE_IDENTITY_LOOKUP_BY_SUFFIX, struct LookupMessage, NULL), GNUNET_MQ_hd_var_size(get_default_message, GNUNET_MESSAGE_TYPE_IDENTITY_GET_DEFAULT, struct GetDefaultMessage, NULL), GNUNET_MQ_hd_var_size(set_default_message, GNUNET_MESSAGE_TYPE_IDENTITY_SET_DEFAULT, struct SetDefaultMessage, NULL), GNUNET_MQ_hd_var_size(create_message, GNUNET_MESSAGE_TYPE_IDENTITY_CREATE, struct CreateRequestMessage, NULL), GNUNET_MQ_hd_var_size(rename_message, GNUNET_MESSAGE_TYPE_IDENTITY_RENAME, struct RenameMessage, NULL), GNUNET_MQ_hd_var_size(delete_message, GNUNET_MESSAGE_TYPE_IDENTITY_DELETE, struct DeleteMessage, NULL), GNUNET_MQ_handler_end())
Define "main" method using service macro.
uint16_t reserved
Always zero.
Definition: identity.h:179
int GNUNET_DISK_file_test(const char *fil)
Check that fil corresponds to a filename (of a file that exists and that is not a directory)...
Definition: disk.c:669
struct GNUNET_CRYPTO_EcdsaPrivateKey private_key
The private key.
Definition: identity.h:154
Message from client to GNS service to lookup records.
Definition: gns.h:36
#define GNUNET_MESSAGE_TYPE_IDENTITY_START
First message send from identity client to service (to subscribe to updates).
struct Ego * prev
We keep egos in a DLL.
#define GNUNET_MESSAGE_TYPE_IDENTITY_SET_DEFAULT
Client sets default identity; or service informs about default identity.
static struct GNUNET_SERVICE_Handle * service
Handle to our service instance.
static int check_delete_message(void *cls, const struct DeleteMessage *msg)
Checks a GNUNET_MESSAGE_TYPE_IDENTITY_DELETE message.
The notification context is the key datastructure for a convenience API used for transmission of noti...
Definition: nc.c:77
Used from service to client as a result to the GET_DEFAULT message, used from client to service to SE...
Definition: identity.h:134
struct GNUNET_MessageHeader * msg
Definition: 005.c:2
#define GNUNET_MESSAGE_TYPE_IDENTITY_DELETE
Delete identity (client->service).
struct GNUNET_MessageHeader header
Type: GNUNET_MESSAGE_TYPE_IDENTITY_CREATE.
Definition: identity.h:169
struct Ego * next
We keep egos in a DLL.
#define GNUNET_CONTAINER_DLL_insert(head, tail, element)
Insert an element at the head of a DLL.
int GNUNET_CONFIGURATION_write(struct GNUNET_CONFIGURATION_Handle *cfg, const char *filename)
Write configuration file.
Common type definitions for the identity service and API.
static void * client_connect_cb(void *cls, struct GNUNET_SERVICE_Client *client, struct GNUNET_MQ_Handle *mq)
Add a client to our list of active clients.
Handle to a service.
Definition: service.c:116
uint16_t reserved
Always zero.
Definition: identity.h:123
static char * get_ego_filename(struct Ego *ego)
Get the name of the file we use to store a given ego.
static void send_result_code(struct GNUNET_SERVICE_Client *client, uint32_t result_code, const char *emsg)
Send a result code back to the client.
static void handle_lookup_message(void *cls, const struct LookupMessage *message)
Handler for LOOKUP message from client, sends information about ONE identity to the client immediatel...
struct GNUNET_MQ_Handle * GNUNET_SERVICE_client_get_mq(struct GNUNET_SERVICE_Client *c)
Obtain the message queue of c.
Definition: service.c:2734
int GNUNET_DISK_directory_create(const char *dir)
Implementation of "mkdir -p".
Definition: disk.c:714
struct GNUNET_SCHEDULER_Task * GNUNET_SCHEDULER_add_shutdown(GNUNET_SCHEDULER_TaskCallback task, void *task_cls)
Schedule a new task to be run on shutdown, that is when a CTRL-C signal is received, or when GNUNET_SCHEDULER_shutdown() is being invoked.
Definition: scheduler.c:1293
struct GNUNET_MessageHeader header
Type: GNUNET_MESSAGE_TYPE_IDENTITY_UPDATE.
Definition: identity.h:82
struct GNUNET_STATISTICS_Handle * GNUNET_STATISTICS_create(const char *subsystem, const struct GNUNET_CONFIGURATION_Handle *cfg)
Get handle for the statistics service.
static int check_create_message(void *cls, const struct CreateRequestMessage *msg)
Checks a GNUNET_MESSAGE_TYPE_IDENTITY_CREATE message.
uint16_t name_len
Number of bytes in service name string including 0-termination, in NBO.
Definition: identity.h:144
static void handle_set_default_message(void *cls, const struct SetDefaultMessage *sdm)
Handler for SET_DEFAULT message from client, updates default identity for some service.
uint16_t name_len
Number of bytes in service name string including 0-termination, in NBO.
Definition: identity.h:118
struct GNUNET_MessageHeader header
Type: GNUNET_MESSAGE_TYPE_IDENTITY_GET_DEFAULT.
Definition: identity.h:113
uint16_t old_name_len
Number of characters in the old name including 0-termination, in NBO.
Definition: identity.h:204
Client requests renaming of an identity.
Definition: identity.h:194
struct GNUNET_CRYPTO_EcdsaPrivateKey private_key
The private key.
Definition: identity.h:98
#define GNUNET_MQ_hd_fixed_size(name, code, str, ctx)
uint16_t reserved
Always zero.
Definition: identity.h:235
static struct Experiment * e
int GNUNET_DISK_directory_create_for_file(const char *filename)
Create the directory structure for storing a file.
Definition: disk.c:833
static void handle_lookup_by_suffix_message(void *cls, const struct LookupMessage *message)
Handler for LOOKUP_BY_SUFFIX message from client, sends information about ONE identity to the client ...
#define GNUNET_NO
Definition: gnunet_common.h:81
struct GNUNET_CRYPTO_EcdsaPrivateKey * pk
Private key of the ego.
#define GNUNET_MESSAGE_TYPE_IDENTITY_UPDATE
Update about identity status from service to clients.
static struct GNUNET_IDENTITY_Handle * id
Handle to identity service.
#define GNUNET_OK
Named constants for return values.
Definition: gnunet_common.h:78
#define GNUNET_new(type)
Allocate a struct or union of the given type.
Private ECC key encoded for transmission.
struct GNUNET_CONFIGURATION_Handle * GNUNET_CONFIGURATION_create(void)
Create a new configuration object.
int GNUNET_CONFIGURATION_parse(struct GNUNET_CONFIGURATION_Handle *cfg, const char *filename)
Parse a configuration file, add all of the options in the file to the configuration environment...
int GNUNET_DISK_directory_scan(const char *dir_name, GNUNET_FileNameCallback callback, void *callback_cls)
Scan a directory for files.
Definition: disk.c:1233
uint16_t size
The length of the struct (in bytes, including the length field itself), in big-endian format...
void GNUNET_STATISTICS_destroy(struct GNUNET_STATISTICS_Handle *h, int sync_first)
Destroy a handle (free all state associated with it).
void GNUNET_SCHEDULER_shutdown(void)
Request the shutdown of a scheduler.
Definition: scheduler.c:524
Handle for the service.
#define GNUNET_strdup(a)
Wrapper around GNUNET_xstrdup_.
uint16_t name_len
Number of bytes in identity name string including 0-termination, in NBO.
Definition: identity.h:174
void GNUNET_notification_context_add(struct GNUNET_NotificationContext *nc, struct GNUNET_MQ_Handle *mq)
Add a subscriber to the notification context.
Definition: nc.c:164
static int check_lookup_message(void *cls, const struct LookupMessage *message)
Handler for LOOKUP message from client, sends information about ONE identity to the client immediatel...
ssize_t GNUNET_DISK_fn_write(const char *fn, const void *buffer, size_t n, enum GNUNET_DISK_AccessPermissions mode)
Write a buffer to a file.
Definition: disk.c:1203
Closure for &#39;handle_ego_rename&#39;.
#define GNUNET_break(cond)
Use this for internal assertion violations that are not fatal (can be handled) but should not occur...
#define UNLINK(f)
Definition: plibc.h:666
#define _(String)
GNU gettext support macro.
Definition: platform.h:208
static char * section
Name of the section.
Definition: gnunet-config.c:33
static const struct GNUNET_CONFIGURATION_Handle * cfg
Handle to our current configuration.
Handle to a client that is connected to a service.
Definition: service.c:249
uint16_t reserved
Always zero.
Definition: identity.h:149
int GNUNET_asprintf(char **buf, const char *format,...)
Like asprintf, just portable.
static void handle_create_message(void *cls, const struct CreateRequestMessage *crm)
Handler for CREATE message from client, creates new identity.
#define GNUNET_MQ_msg_extra(mvar, esize, type)
Allocate an envelope, with extra space allocated after the space needed by the message struct...
Definition: gnunet_mq_lib.h:52
uint16_t type
The type of the message (GNUNET_MESSAGE_TYPE_XXXX), in big-endian format.
static int check_set_default_message(void *cls, const struct SetDefaultMessage *msg)
Checks a GNUNET_MESSAGE_TYPE_IDENTITY_SET_DEFAULT message.
#define GNUNET_MQ_check_zero_termination(m)
Insert code for a "check_" function that verifies that a given variable-length message received over ...
#define GNUNET_memcpy(dst, src, n)
static void handle_ego_delete(void *cls, const char *section)
An ego was removed, remove it from all subsystems where it is currently set as the default...
void GNUNET_log_config_missing(enum GNUNET_ErrorType kind, const char *section, const char *option)
Log error message about missing configuration option.
static struct GNUNET_STATISTICS_Handle * stats
Handle to the statistics service.
static void client_disconnect_cb(void *cls, struct GNUNET_SERVICE_Client *client, void *app_ctx)
Called whenever a client is disconnected.
#define GNUNET_log_strerror_file(level, cmd, filename)
Log an error message at log-level &#39;level&#39; that indicates a failure of the command &#39;cmd&#39; with the mess...
#define GNUNET_MQ_hd_var_size(name, code, str, ctx)
static char * fn
Filename of the unique file.
static struct GNUNET_MQ_Envelope * create_set_default_message(struct Ego *ego, const char *servicename)
Create a set default message with information about the current state of an ego.
#define GNUNET_MESSAGE_TYPE_IDENTITY_LOOKUP
First message send from identity client to service to lookup a single ego.
Client requests creation of an identity.
Definition: identity.h:164
void GNUNET_CONFIGURATION_destroy(struct GNUNET_CONFIGURATION_Handle *cfg)
Destroy configuration object.
static char * filename
static int check_rename_message(void *cls, const struct RenameMessage *msg)
Checks a GNUNET_MESSAGE_TYPE_IDENTITY_RENAME message.
char * identifier
String identifier for the ego.
void GNUNET_CONFIGURATION_set_value_string(struct GNUNET_CONFIGURATION_Handle *cfg, const char *section, const char *option, const char *value)
Set a configuration value that should be a string.
void GNUNET_SERVICE_client_mark_monitor(struct GNUNET_SERVICE_Client *c)
Set the &#39;monitor&#39; flag on this client.
Definition: service.c:2704
static void shutdown_task(void *cls)
Task run during shutdown.
#define DIR_SEPARATOR
Definition: plibc.h:631
static void run(void *cls, const struct GNUNET_CONFIGURATION_Handle *c, struct GNUNET_SERVICE_Handle *service)
Handle network size estimate clients.
struct GNUNET_MessageHeader header
Type: GNUNET_MESSAGE_TYPE_IDENTITY_DELETE.
Definition: identity.h:225
Client requests deletion of an identity.
Definition: identity.h:220
static void handle_rename_message(void *cls, const struct RenameMessage *rm)
Handler for RENAME message from client, creates new identity.
int 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.
const char * new_name
New name.
#define GNUNET_MESSAGE_TYPE_IDENTITY_LOOKUP_BY_SUFFIX
First message send from identity client to service to lookup a single ego matching the given suffix (...
#define RENAME(o, n)
Definition: plibc.h:662
#define GNUNET_MESSAGE_TYPE_IDENTITY_CREATE
Create new identity (client->service).
#define GNUNET_SYSERR
Definition: gnunet_common.h:79
static unsigned int size
Size of the "table".
Definition: peer.c:67
static void handle_delete_message(void *cls, const struct DeleteMessage *dm)
Handler for DELETE message from client, creates new identity.
struct GNUNET_CRYPTO_EcdsaPrivateKey * GNUNET_CRYPTO_ecdsa_key_create_from_file(const char *filename)
Create a new private key by reading it from a file.
static struct GNUNET_NotificationContext * nc
Notification context, simplifies client broadcasts.
const char * name
struct GNUNET_MQ_Envelope * env
Definition: 005.c:1
static struct Ego * ego_head
Head of DLL of all egos.
struct GNUNET_MessageHeader header
Type: GNUNET_MESSAGE_TYPE_IDENTITY_SET_DEFAULT.
Definition: identity.h:139
static char * subsystem_cfg_file
Configuration file name where subsystem information is kept.
#define GNUNET_memcmp(a, b)
Compare memory in a and b, where both must be of the same pointer type.
struct GNUNET_NotificationContext * GNUNET_notification_context_create(unsigned int queue_length)
Create a new notification context.
Definition: nc.c:125
Information we keep about each ego.
uint32_t result_code
Status code for the last operation, in NBO.
Definition: identity.h:53
uint16_t name_len
Number of bytes in ego name string including 0-termination, in NBO; 0 if the ego was deleted...
Definition: identity.h:88
Handle to a message queue.
Definition: mq.c:85
static int check_lookup_by_suffix_message(void *cls, const struct LookupMessage *message)
Handler for LOOKUP message from client, sends information about ONE identity to the client immediatel...
uint16_t new_name_len
Number of characters in the new name including 0-termination, in NBO.
Definition: identity.h:209
void GNUNET_notification_context_broadcast(struct GNUNET_NotificationContext *nc, const struct GNUNET_MessageHeader *msg, int can_drop)
Send a message to all subscribers of this context.
Definition: nc.c:192
static void notify_listeners(struct Ego *ego)
Send an updated message for the given ego to all listeners.
configuration data
Definition: configuration.c:85
static int key_cmp(const struct GNUNET_CRYPTO_EcdsaPrivateKey *pk1, const struct GNUNET_CRYPTO_EcdsaPrivateKey *pk2)
Compare the given two private keys for equality.
uint16_t end_of_list
Usually GNUNET_NO, GNUNET_YES to signal end of list.
Definition: identity.h:93
void GNUNET_CONFIGURATION_iterate_sections(const struct GNUNET_CONFIGURATION_Handle *cfg, GNUNET_CONFIGURATION_Section_Iterator iter, void *iter_cls)
Iterate over all sections in the configuration.
struct GNUNET_MQ_Handle * mq
Definition: 003.c:5
#define GNUNET_log(kind,...)
static void handle_start_message(void *cls, const struct GNUNET_MessageHeader *message)
Handler for START message from client, sends information about all identities to the client immediate...
#define GNUNET_MESSAGE_TYPE_IDENTITY_GET_DEFAULT
Client requests to know default identity for a subsystem.
int 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.
#define GNUNET_MESSAGE_TYPE_IDENTITY_RENAME
Rename existing identity (client->service).
static char * ego_directory
Directory where we store the identities.
uint16_t name_len
Number of characters in the name including 0-termination, in NBO.
Definition: identity.h:230
static void handle_get_default_message(void *cls, const struct GetDefaultMessage *gdm)
Handler for GET_DEFAULT message from client, returns default identity for some service.
static int check_get_default_message(void *cls, const struct GetDefaultMessage *msg)
Checks a GNUNET_MESSAGE_TYPE_IDENTITY_GET_DEFAULT message.
struct GNUNET_MessageHeader header
Type: GNUNET_MESSAGE_TYPE_IDENTITY_RENAME.
Definition: identity.h:199
Header for all communications.
#define GNUNET_YES
Definition: gnunet_common.h:80
void GNUNET_notification_context_destroy(struct GNUNET_NotificationContext *nc)
Destroy the context, force disconnect for all subscribers.
Definition: nc.c:141
#define GNUNET_MESSAGE_TYPE_IDENTITY_RESULT_CODE
Generic response from identity service with success and/or error message.
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:353
const char * old_name
Old name.
Client requests knowledge about default identity for a subsystem from identity service.
Definition: identity.h:108
#define DIR_SEPARATOR_STR
Definition: plibc.h:632
static struct Ego * ego_tail
Tail of DLL of all egos.
static int process_ego_file(void *cls, const char *filename)
Process the given file from the "EGODIR".
static struct GNUNET_CONFIGURATION_Handle * subsystem_cfg
Handle to subsystem configuration which for each subsystem contains the name of the default ego...
void GNUNET_SERVICE_client_disable_continue_warning(struct GNUNET_SERVICE_Client *c)
Disable the warning the server issues if a message is not acknowledged in a timely fashion...
Definition: service.c:2559
static void handle_ego_rename(void *cls, const char *section)
An ego was renamed; rename it in all subsystems where it is currently set as the default.
void GNUNET_SERVICE_client_continue(struct GNUNET_SERVICE_Client *c)
Continue receiving further messages from the given client.
Definition: service.c:2533
#define GNUNET_MQ_handler_end()
End-marker for the handlers array.
static struct GNUNET_MQ_Envelope * create_update_message(struct Ego *ego)
Create an update message with information about the current state of an ego.
#define GNUNET_malloc(size)
Wrapper around malloc.
Answer from service to client about last operation; GET_DEFAULT maybe answered with this message on f...
Definition: identity.h:42
Service informs client about status of a pseudonym.
Definition: identity.h:77
#define GNUNET_free(ptr)
Wrapper around free.
void GNUNET_STRINGS_utf8_tolower(const char *input, char *output)
Convert the utf-8 input string to lower case.
Definition: strings.c:558
#define gettext_noop(String)
Definition: gettext.h:69