GNUnet  0.10.x
namestore_api.c
Go to the documentation of this file.
1 /*
2  This file is part of GNUnet.
3  Copyright (C) 2010-2013, 2016 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_util_lib.h"
31 #include "gnunet_crypto_lib.h"
32 #include "gnunet_constants.h"
33 #include "gnunet_dnsparser_lib.h"
34 #include "gnunet_arm_service.h"
35 #include "gnunet_signatures.h"
36 #include "gnunet_gns_service.h"
38 #include "namestore.h"
39 
40 
41 #define LOG(kind, ...) GNUNET_log_from(kind, "namestore-api", __VA_ARGS__)
42 
47 #define NAMESTORE_DELAY_TOLERANCE GNUNET_TIME_UNIT_MINUTES
48 
58 
63 
68 
73 
77  void *cont_cls;
78 
83 
87  void *proc_cls;
88 
93 
97  void *error_cb_cls;
98 
104 
109 
113  uint32_t op_id;
114 };
115 
116 
125 
130 
135 
140 
145 
150 
154  void *proc_cls;
155 
160 
165 
171 
176 
180  uint32_t op_id;
181 };
182 
183 
192 
197 
202 
207 
212 
217 
222 
226  struct GNUNET_TIME_Relative reconnect_delay;
227 
232 
236  uint32_t last_op_id_used;
237 };
238 
239 
245 static void
247 
248 
256 static struct GNUNET_NAMESTORE_QueueEntry *
257 find_qe(struct GNUNET_NAMESTORE_Handle *h, uint32_t rid)
258 {
260 
261  for (qe = h->op_head; qe != NULL; qe = qe->next)
262  if (qe->op_id == rid)
263  return qe;
264  return NULL;
265 }
266 
267 
275 static struct GNUNET_NAMESTORE_ZoneIterator *
276 find_zi(struct GNUNET_NAMESTORE_Handle *h, uint32_t rid)
277 {
279 
280  for (ze = h->z_head; ze != NULL; ze = ze->next)
281  if (ze->op_id == rid)
282  return ze;
283  return NULL;
284 }
285 
286 
292 static void
294 {
295  struct GNUNET_NAMESTORE_Handle *h = qe->h;
296 
298  if (NULL != qe->env)
299  GNUNET_MQ_discard(qe->env);
300  if (NULL != qe->timeout_task)
302  GNUNET_free(qe);
303 }
304 
305 
311 static void
313 {
314  struct GNUNET_NAMESTORE_Handle *h = ze->h;
315 
317  if (NULL != ze->env)
318  GNUNET_MQ_discard(ze->env);
319  GNUNET_free(ze);
320 }
321 
322 
332 static int
333 check_rd(size_t rd_len, const void *rd_buf, unsigned int rd_count)
334 {
335  struct GNUNET_GNSRECORD_Data rd[rd_count];
336 
337  if (GNUNET_OK !=
338  GNUNET_GNSRECORD_records_deserialize(rd_len, rd_buf, rd_count, rd))
339  {
340  GNUNET_break(0);
341  return GNUNET_SYSERR;
342  }
343  return GNUNET_OK;
344 }
345 
346 
354 static void
356  const struct RecordStoreResponseMessage *msg)
357 {
358  struct GNUNET_NAMESTORE_Handle *h = cls;
360  int res;
361  const char *emsg;
362 
363  qe = find_qe(h, ntohl(msg->gns_header.r_id));
364  res = ntohl(msg->op_result);
366  "Received RECORD_STORE_RESPONSE with result %d\n",
367  res);
368  /* TODO: add actual error message from namestore to response... */
369  if (GNUNET_SYSERR == res)
370  emsg = _("Namestore failed to store record\n");
371  else
372  emsg = NULL;
373  if (NULL != qe->cont)
374  qe->cont(qe->cont_cls, res, emsg);
375  free_qe(qe);
376 }
377 
378 
387 static int
389 {
390  const char *name;
391  size_t exp_msg_len;
392  size_t msg_len;
393  size_t name_len;
394  size_t rd_len;
395 
396  (void)cls;
397  rd_len = ntohs(msg->rd_len);
398  msg_len = ntohs(msg->gns_header.header.size);
399  name_len = ntohs(msg->name_len);
400  exp_msg_len = sizeof(*msg) + name_len + rd_len;
401  if (msg_len != exp_msg_len)
402  {
403  GNUNET_break(0);
404  return GNUNET_SYSERR;
405  }
406  name = (const char *)&msg[1];
407  if ((name_len > 0) && ('\0' != name[name_len - 1]))
408  {
409  GNUNET_break(0);
410  return GNUNET_SYSERR;
411  }
412  if (GNUNET_NO == ntohs(msg->found))
413  {
414  if (0 != ntohs(msg->rd_count))
415  {
416  GNUNET_break(0);
417  return GNUNET_SYSERR;
418  }
419  return GNUNET_OK;
420  }
421  return check_rd(rd_len, &name[name_len], ntohs(msg->rd_count));
422 }
423 
424 
432 static void
434 {
435  struct GNUNET_NAMESTORE_Handle *h = cls;
437  const char *name;
438  const char *rd_tmp;
439  size_t name_len;
440  size_t rd_len;
441  unsigned int rd_count;
442 
443  LOG(GNUNET_ERROR_TYPE_DEBUG, "Received RECORD_LOOKUP_RESULT\n");
444  qe = find_qe(h, ntohl(msg->gns_header.r_id));
445  if (NULL == qe)
446  return;
447  rd_len = ntohs(msg->rd_len);
448  rd_count = ntohs(msg->rd_count);
449  name_len = ntohs(msg->name_len);
450  name = (const char *)&msg[1];
451  if (GNUNET_NO == ntohs(msg->found))
452  {
453  /* label was not in namestore */
454  if (NULL != qe->proc)
455  qe->proc(qe->proc_cls, &msg->private_key, name, 0, NULL);
456  free_qe(qe);
457  return;
458  }
459 
460  rd_tmp = &name[name_len];
461  {
462  struct GNUNET_GNSRECORD_Data rd[rd_count];
463 
465  GNUNET_OK ==
466  GNUNET_GNSRECORD_records_deserialize(rd_len, rd_tmp, rd_count, rd));
467  if (0 == name_len)
468  name = NULL;
469  if (NULL != qe->proc)
470  qe->proc(qe->proc_cls,
471  &msg->private_key,
472  name,
473  rd_count,
474  (rd_count > 0) ? rd : NULL);
475  }
476  free_qe(qe);
477 }
478 
479 
488 static int
489 check_record_result(void *cls, const struct RecordResultMessage *msg)
490 {
491  static struct GNUNET_CRYPTO_EcdsaPrivateKey priv_dummy;
492  const char *name;
493  size_t msg_len;
494  size_t name_len;
495  size_t rd_len;
496 
497  (void)cls;
498  rd_len = ntohs(msg->rd_len);
499  msg_len = ntohs(msg->gns_header.header.size);
500  name_len = ntohs(msg->name_len);
501  if (0 != ntohs(msg->reserved))
502  {
503  GNUNET_break(0);
504  return GNUNET_SYSERR;
505  }
506  if (msg_len != sizeof(struct RecordResultMessage) + name_len + rd_len)
507  {
508  GNUNET_break(0);
509  return GNUNET_SYSERR;
510  }
511  name = (const char *)&msg[1];
512  if ((0 == name_len) || ('\0' != name[name_len - 1]))
513  {
514  GNUNET_break(0);
515  return GNUNET_SYSERR;
516  }
517  if (0 == GNUNET_memcmp(&msg->private_key, &priv_dummy))
518  {
519  GNUNET_break(0);
520  return GNUNET_SYSERR;
521  }
522  return check_rd(rd_len, &name[name_len], ntohs(msg->rd_count));
523 }
524 
525 
533 static void
535 {
536  struct GNUNET_NAMESTORE_Handle *h = cls;
539  const char *name;
540  const char *rd_tmp;
541  size_t name_len;
542  size_t rd_len;
543  unsigned int rd_count;
544 
545  LOG(GNUNET_ERROR_TYPE_DEBUG, "Received RECORD_RESULT\n");
546  rd_len = ntohs(msg->rd_len);
547  rd_count = ntohs(msg->rd_count);
548  name_len = ntohs(msg->name_len);
549  ze = find_zi(h, ntohl(msg->gns_header.r_id));
550  qe = find_qe(h, ntohl(msg->gns_header.r_id));
551  if ((NULL == ze) && (NULL == qe))
552  return; /* rid not found */
553  if ((NULL != ze) && (NULL != qe))
554  {
555  GNUNET_break(0); /* rid ambigous */
556  force_reconnect(h);
557  return;
558  }
559  name = (const char *)&msg[1];
560  rd_tmp = &name[name_len];
561  {
562  struct GNUNET_GNSRECORD_Data rd[rd_count];
563 
565  GNUNET_OK ==
566  GNUNET_GNSRECORD_records_deserialize(rd_len, rd_tmp, rd_count, rd));
567  if (0 == name_len)
568  name = NULL;
569  if (NULL != qe)
570  {
571  if (NULL != qe->proc)
572  qe->proc(qe->proc_cls,
573  &msg->private_key,
574  name,
575  rd_count,
576  (rd_count > 0) ? rd : NULL);
577  free_qe(qe);
578  return;
579  }
580  if (NULL != ze)
581  {
582  if (NULL != ze->proc)
583  ze->proc(ze->proc_cls, &msg->private_key, name, rd_count, rd);
584  return;
585  }
586  }
587  GNUNET_assert(0);
588 }
589 
590 
598 static void
600 {
601  struct GNUNET_NAMESTORE_Handle *h = cls;
604 
605  LOG(GNUNET_ERROR_TYPE_DEBUG, "Received RECORD_RESULT_END\n");
606  ze = find_zi(h, ntohl(msg->r_id));
607  qe = find_qe(h, ntohl(msg->r_id));
608  if ((NULL == ze) && (NULL == qe))
609  return; /* rid not found */
610  if ((NULL != ze) && (NULL != qe))
611  {
612  GNUNET_break(0); /* rid ambigous */
613  force_reconnect(h);
614  return;
615  }
616  LOG(GNUNET_ERROR_TYPE_DEBUG, "Zone iteration completed!\n");
617  if (NULL == ze)
618  {
619  GNUNET_break(0);
620  force_reconnect(h);
621  return;
622  }
623  if (NULL != ze->finish_cb)
624  ze->finish_cb(ze->finish_cb_cls);
625  free_ze(ze);
626 }
627 
628 
637 static int
639  const struct ZoneToNameResponseMessage *msg)
640 {
641  size_t name_len;
642  size_t rd_ser_len;
643  const char *name_tmp;
644 
645  (void)cls;
646  if (GNUNET_OK != ntohs(msg->res))
647  return GNUNET_OK;
648  name_len = ntohs(msg->name_len);
649  rd_ser_len = ntohs(msg->rd_len);
650  if (ntohs(msg->gns_header.header.size) !=
651  sizeof(struct ZoneToNameResponseMessage) + name_len + rd_ser_len)
652  {
653  GNUNET_break(0);
654  return GNUNET_SYSERR;
655  }
656  name_tmp = (const char *)&msg[1];
657  if ((name_len > 0) && ('\0' != name_tmp[name_len - 1]))
658  {
659  GNUNET_break(0);
660  return GNUNET_SYSERR;
661  }
662  return check_rd(rd_ser_len, &name_tmp[name_len], ntohs(msg->rd_count));
663 }
664 
665 
673 static void
675  const struct ZoneToNameResponseMessage *msg)
676 {
677  struct GNUNET_NAMESTORE_Handle *h = cls;
679  int res;
680  size_t name_len;
681  size_t rd_ser_len;
682  unsigned int rd_count;
683  const char *name_tmp;
684  const char *rd_tmp;
685 
686  LOG(GNUNET_ERROR_TYPE_DEBUG, "Received ZONE_TO_NAME_RESPONSE\n");
687  qe = find_qe(h, ntohl(msg->gns_header.r_id));
688  res = ntohs(msg->res);
689  switch (res)
690  {
691  case GNUNET_SYSERR:
693  "An error occurred during zone to name operation\n");
694  break;
695 
696  case GNUNET_NO:
698  "Namestore has no result for zone to name mapping \n");
699  if (NULL != qe->proc)
700  qe->proc(qe->proc_cls, &msg->zone, NULL, 0, NULL);
701  free_qe(qe);
702  return;
703 
704  case GNUNET_YES:
706  "Namestore has result for zone to name mapping \n");
707  name_len = ntohs(msg->name_len);
708  rd_count = ntohs(msg->rd_count);
709  rd_ser_len = ntohs(msg->rd_len);
710  name_tmp = (const char *)&msg[1];
711  rd_tmp = &name_tmp[name_len];
712  {
713  struct GNUNET_GNSRECORD_Data rd[rd_count];
714 
717  rd_tmp,
718  rd_count,
719  rd));
720  /* normal end, call continuation with result */
721  if (NULL != qe->proc)
722  qe->proc(qe->proc_cls, &msg->zone, name_tmp, rd_count, rd);
723  /* return is important here: break would call continuation with error! */
724  free_qe(qe);
725  return;
726  }
727 
728  default:
729  GNUNET_break(0);
730  force_reconnect(h);
731  return;
732  }
733  /* error case, call continuation with error */
734  if (NULL != qe->error_cb)
735  qe->error_cb(qe->error_cb_cls);
736  free_qe(qe);
737 }
738 
739 
748 static void
749 mq_error_handler(void *cls, enum GNUNET_MQ_Error error)
750 {
751  struct GNUNET_NAMESTORE_Handle *h = cls;
752 
753  (void)error;
754  force_reconnect(h);
755 }
756 
757 
763 static void
765 {
766  struct GNUNET_MQ_MessageHandler handlers[] =
767  { GNUNET_MQ_hd_fixed_size(record_store_response,
770  h),
771  GNUNET_MQ_hd_var_size(zone_to_name_response,
774  h),
775  GNUNET_MQ_hd_var_size(record_result,
777  struct RecordResultMessage,
778  h),
779  GNUNET_MQ_hd_fixed_size(record_result_end,
782  h),
783  GNUNET_MQ_hd_var_size(lookup_result,
786  h),
790 
791  GNUNET_assert(NULL == h->mq);
792  h->mq =
793  GNUNET_CLIENT_connect(h->cfg, "namestore", handlers, &mq_error_handler, h);
794  if (NULL == h->mq)
795  return;
796  /* re-transmit pending requests that waited for a reconnect... */
797  for (it = h->z_head; NULL != it; it = it->next)
798  {
799  GNUNET_MQ_send(h->mq, it->env);
800  it->env = NULL;
801  }
802  for (qe = h->op_head; NULL != qe; qe = qe->next)
803  {
804  GNUNET_MQ_send(h->mq, qe->env);
805  qe->env = NULL;
806  }
807 }
808 
809 
815 static void
816 reconnect_task(void *cls)
817 {
818  struct GNUNET_NAMESTORE_Handle *h = cls;
819 
820  h->reconnect_task = NULL;
821  reconnect(h);
822 }
823 
824 
830 static void
832 {
835 
836  GNUNET_MQ_destroy(h->mq);
837  h->mq = NULL;
838  while (NULL != (ze = h->z_head))
839  {
840  if (NULL != ze->error_cb)
841  ze->error_cb(ze->error_cb_cls);
842  free_ze(ze);
843  }
844  while (NULL != (qe = h->op_head))
845  {
846  if (NULL != qe->error_cb)
847  qe->error_cb(qe->error_cb_cls);
848  if (NULL != qe->cont)
849  qe->cont(qe->cont_cls,
851  "failure in communication with namestore service");
852  free_qe(qe);
853  }
854 
855  GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, "Reconnecting to namestore\n");
857  h->reconnect_task =
859 }
860 
861 
868 static uint32_t
870 {
871  return h->last_op_id_used++;
872 }
873 
874 
883 {
884  struct GNUNET_NAMESTORE_Handle *h;
885 
887  h->cfg = cfg;
888  reconnect(h);
889  if (NULL == h->mq)
890  {
891  GNUNET_free(h);
892  return NULL;
893  }
894  return h;
895 }
896 
897 
904 void
906 {
909 
910  LOG(GNUNET_ERROR_TYPE_DEBUG, "Cleaning up\n");
911  GNUNET_break(NULL == h->op_head);
912  while (NULL != (q = h->op_head))
913  {
915  GNUNET_free(q);
916  }
917  GNUNET_break(NULL == h->z_head);
918  while (NULL != (z = h->z_head))
919  {
921  GNUNET_free(z);
922  }
923  if (NULL != h->mq)
924  {
925  GNUNET_MQ_destroy(h->mq);
926  h->mq = NULL;
927  }
928  if (NULL != h->reconnect_task)
929  {
931  h->reconnect_task = NULL;
932  }
933  GNUNET_free(h);
934 }
935 
936 
943 static void
944 warn_delay(void *cls)
945 {
946  struct GNUNET_NAMESTORE_QueueEntry *qe = cls;
947 
948  qe->timeout_task = NULL;
950  "Did not receive response from namestore after %s!\n",
952  GNUNET_YES));
953  if (NULL != qe->cont)
954  {
955  qe->cont(qe->cont_cls, GNUNET_SYSERR, "timeout");
956  qe->cont = NULL;
957  }
959 }
960 
961 
978  struct GNUNET_NAMESTORE_Handle *h,
979  const struct GNUNET_CRYPTO_EcdsaPrivateKey *pkey,
980  const char *label,
981  unsigned int rd_count,
982  const struct GNUNET_GNSRECORD_Data *rd,
984  void *cont_cls)
985 {
987  struct GNUNET_MQ_Envelope *env;
988  char *name_tmp;
989  char *rd_ser;
990  ssize_t rd_ser_len;
991  size_t name_len;
992  uint32_t rid;
993  struct RecordStoreMessage *msg;
994  ssize_t sret;
995 
996  name_len = strlen(label) + 1;
997  if (name_len > MAX_NAME_LEN)
998  {
999  GNUNET_break(0);
1000  return NULL;
1001  }
1002  rd_ser_len = GNUNET_GNSRECORD_records_get_size(rd_count, rd);
1003  if (rd_ser_len < 0)
1004  {
1005  GNUNET_break(0);
1006  return NULL;
1007  }
1008  if (rd_ser_len > UINT16_MAX)
1009  {
1010  GNUNET_break(0);
1011  return NULL;
1012  }
1013  rid = get_op_id(h);
1015  qe->h = h;
1016  qe->cont = cont;
1017  qe->cont_cls = cont_cls;
1018  qe->op_id = rid;
1020 
1021  /* setup msg */
1022  env = GNUNET_MQ_msg_extra(msg,
1023  name_len + rd_ser_len,
1025  msg->gns_header.r_id = htonl(rid);
1026  msg->name_len = htons(name_len);
1027  msg->rd_count = htons(rd_count);
1028  msg->rd_len = htons(rd_ser_len);
1029  msg->reserved = htons(0);
1030  msg->private_key = *pkey;
1031 
1032  name_tmp = (char *)&msg[1];
1033  GNUNET_memcpy(name_tmp, label, name_len);
1034  rd_ser = &name_tmp[name_len];
1035  sret = GNUNET_GNSRECORD_records_serialize(rd_count, rd, rd_ser_len, rd_ser);
1036  if ((0 > sret) || (sret != rd_ser_len))
1037  {
1038  GNUNET_break(0);
1039  GNUNET_free(env);
1040  return NULL;
1041  }
1042  GNUNET_assert(rd_ser_len == sret);
1044  "Sending NAMESTORE_RECORD_STORE message for name `%s' with %u records\n",
1045  label,
1046  rd_count);
1047  qe->timeout_task =
1049  if (NULL == h->mq)
1050  {
1051  qe->env = env;
1053  "Delaying NAMESTORE_RECORD_STORE message as namestore is not ready!\n");
1054  }
1055  else
1056  {
1057  GNUNET_MQ_send(h->mq, env);
1058  }
1059  return qe;
1060 }
1061 
1062 
1075  const struct GNUNET_CRYPTO_EcdsaPrivateKey *pkey,
1076  const char *nick,
1078  void *cont_cls)
1079 {
1080  struct GNUNET_GNSRECORD_Data rd;
1081 
1082  if (NULL == h->mq)
1083  return NULL;
1084  memset(&rd, 0, sizeof(rd));
1085  rd.data = nick;
1086  rd.data_size = strlen(nick) + 1;
1091  pkey,
1093  1,
1094  &rd,
1095  cont,
1096  cont_cls);
1097 }
1098 
1099 
1114  struct GNUNET_NAMESTORE_Handle *h,
1115  const struct GNUNET_CRYPTO_EcdsaPrivateKey *pkey,
1116  const char *label,
1118  void *error_cb_cls,
1120  void *rm_cls)
1121 {
1123  struct GNUNET_MQ_Envelope *env;
1124  struct LabelLookupMessage *msg;
1125  size_t label_len;
1126 
1127  if (1 == (label_len = strlen(label) + 1))
1128  {
1129  GNUNET_break(0);
1130  return NULL;
1131  }
1132 
1134  qe->h = h;
1135  qe->error_cb = error_cb;
1136  qe->error_cb_cls = error_cb_cls;
1137  qe->proc = rm;
1138  qe->proc_cls = rm_cls;
1139  qe->op_id = get_op_id(h);
1141 
1142  env = GNUNET_MQ_msg_extra(msg,
1143  label_len,
1145  msg->gns_header.r_id = htonl(qe->op_id);
1146  msg->zone = *pkey;
1147  msg->label_len = htonl(label_len);
1148  GNUNET_memcpy(&msg[1], label, label_len);
1149  if (NULL == h->mq)
1150  qe->env = env;
1151  else
1152  GNUNET_MQ_send(h->mq, env);
1153  return qe;
1154 }
1155 
1156 
1174  struct GNUNET_NAMESTORE_Handle *h,
1175  const struct GNUNET_CRYPTO_EcdsaPrivateKey *zone,
1176  const struct GNUNET_CRYPTO_EcdsaPublicKey *value_zone,
1178  void *error_cb_cls,
1180  void *proc_cls)
1181 {
1183  struct GNUNET_MQ_Envelope *env;
1184  struct ZoneToNameMessage *msg;
1185  uint32_t rid;
1186 
1187  rid = get_op_id(h);
1189  qe->h = h;
1190  qe->error_cb = error_cb;
1191  qe->error_cb_cls = error_cb_cls;
1192  qe->proc = proc;
1193  qe->proc_cls = proc_cls;
1194  qe->op_id = rid;
1196 
1198  msg->gns_header.r_id = htonl(rid);
1199  msg->zone = *zone;
1200  msg->value_zone = *value_zone;
1201  if (NULL == h->mq)
1202  qe->env = env;
1203  else
1204  GNUNET_MQ_send(h->mq, env);
1205  return qe;
1206 }
1207 
1208 
1230  struct GNUNET_NAMESTORE_Handle *h,
1231  const struct GNUNET_CRYPTO_EcdsaPrivateKey *zone,
1233  void *error_cb_cls,
1235  void *proc_cls,
1237  void *finish_cb_cls)
1238 {
1239  struct GNUNET_NAMESTORE_ZoneIterator *it;
1240  struct GNUNET_MQ_Envelope *env;
1242  uint32_t rid;
1243 
1244  LOG(GNUNET_ERROR_TYPE_DEBUG, "Sending ZONE_ITERATION_START message\n");
1245  rid = get_op_id(h);
1247  it->h = h;
1248  it->error_cb = error_cb;
1249  it->error_cb_cls = error_cb_cls;
1250  it->finish_cb = finish_cb;
1251  it->finish_cb_cls = finish_cb_cls;
1252  it->proc = proc;
1253  it->proc_cls = proc_cls;
1254  it->op_id = rid;
1255  if (NULL != zone)
1256  it->zone = *zone;
1259  msg->gns_header.r_id = htonl(rid);
1260  if (NULL != zone)
1261  msg->zone = *zone;
1262  if (NULL == h->mq)
1263  it->env = env;
1264  else
1265  GNUNET_MQ_send(h->mq, env);
1266  return it;
1267 }
1268 
1269 
1278 void
1280  uint64_t limit)
1281 {
1282  struct GNUNET_NAMESTORE_Handle *h = it->h;
1283  struct ZoneIterationNextMessage *msg;
1284  struct GNUNET_MQ_Envelope *env;
1285 
1287  "Sending ZONE_ITERATION_NEXT message with limit %llu\n",
1288  (unsigned long long)limit);
1290  msg->gns_header.r_id = htonl(it->op_id);
1291  msg->limit = GNUNET_htonll(limit);
1292  GNUNET_MQ_send(h->mq, env);
1293 }
1294 
1295 
1301 void
1303 {
1304  struct GNUNET_NAMESTORE_Handle *h = it->h;
1305  struct GNUNET_MQ_Envelope *env;
1306  struct ZoneIterationStopMessage *msg;
1307 
1308  GNUNET_log(GNUNET_ERROR_TYPE_DEBUG, "Sending ZONE_ITERATION_STOP message\n");
1309  if (NULL != h->mq)
1310  {
1311  env =
1313  msg->gns_header.r_id = htonl(it->op_id);
1314  GNUNET_MQ_send(h->mq, env);
1315  }
1316  free_ze(it);
1317 }
1318 
1319 
1326 void
1328 {
1329  free_qe(qe);
1330 }
1331 
1332 
1333 /* end of namestore_api.c */
#define GNUNET_CONTAINER_DLL_remove(head, tail, element)
Remove an element from a DLL.
struct GNUNET_NAMESTORE_Handle * h
Main handle to access the namestore.
Definition: namestore_api.c:67
struct GNUNET_NAMESTORE_Header gns_header
Type will be GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_STORE_RESPONSE.
Definition: namestore.h:107
struct GNUNET_NAMESTORE_Header gns_header
Type will be GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_STORE.
Definition: namestore.h:61
static struct GNUNET_DATASTORE_QueueEntry * qe
Current operation.
GNUNET_SCHEDULER_TaskCallback error_cb
Function to call on errors.
GNUNET_NETWORK_STRUCT_END ssize_t GNUNET_GNSRECORD_records_get_size(unsigned int rd_count, const struct GNUNET_GNSRECORD_Data *rd)
Calculate how many bytes we will need to serialize the given records.
struct GNUNET_MQ_Envelope * env
Envelope of the message to send to the service, if not yet sent.
struct GNUNET_MessageHeader * msg
Definition: 005.c:2
void(* GNUNET_NAMESTORE_ContinuationWithStatus)(void *cls, int32_t success, const char *emsg)
Continuation called to notify client about result of the operation.
uint32_t label_len
Length of the name.
Definition: namestore.h:128
static char * pkey
Public key of the zone to look in, in ASCII.
static void handle_lookup_result(void *cls, const struct LabelLookupResponseMessage *msg)
Handle an incoming message of type GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_LOOKUP_RESPONSE.
#define GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_TO_NAME_RESPONSE
Service to client: result of zone-to-name lookup.
GNUNET_SCHEDULER_TaskCallback finish_cb
Function to call on completion.
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:900
static int check_zone_to_name_response(void *cls, const struct ZoneToNameResponseMessage *msg)
Handle an incoming message of type GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_TO_NAME_RESPONSE.
GNUNET_NAMESTORE_RecordMonitor proc
Function to call with the records we get back; or NULL.
Definition: namestore_api.c:82
#define GNUNET_GNS_EMPTY_LABEL_AT
String we use to indicate an empty label (top-level entry in the zone).
Ask for next result of zone iteration for the given operation.
Definition: namestore.h:353
uint16_t rd_len
Length of serialized record data.
Definition: namestore.h:158
struct GNUNET_NAMESTORE_QueueEntry * GNUNET_NAMESTORE_records_lookup(struct GNUNET_NAMESTORE_Handle *h, const struct GNUNET_CRYPTO_EcdsaPrivateKey *pkey, const char *label, GNUNET_SCHEDULER_TaskCallback error_cb, void *error_cb_cls, GNUNET_NAMESTORE_RecordMonitor rm, void *rm_cls)
Lookup an item in the namestore.
GNUNET_MQ_Error
Error codes for the queue.
ssize_t GNUNET_GNSRECORD_records_serialize(unsigned int rd_count, const struct GNUNET_GNSRECORD_Data *rd, size_t dest_size, char *dest)
Serialize the given records to the given destination buffer.
struct GNUNET_NAMESTORE_ZoneIterator * GNUNET_NAMESTORE_zone_iteration_start(struct GNUNET_NAMESTORE_Handle *h, const struct GNUNET_CRYPTO_EcdsaPrivateKey *zone, GNUNET_SCHEDULER_TaskCallback error_cb, void *error_cb_cls, GNUNET_NAMESTORE_RecordMonitor proc, void *proc_cls, GNUNET_SCHEDULER_TaskCallback finish_cb, void *finish_cb_cls)
Starts a new zone iteration (used to periodically PUT all of our records into our DHT)...
GNUNET_NAMESTORE_RecordMonitor proc
The continuation to call with the results.
uint16_t reserved
always zero (for alignment)
Definition: namestore.h:274
uint32_t r_id
Request ID in NBO.
Definition: namestore.h:50
uint16_t rd_count
Number of records contained.
Definition: namestore.h:163
#define GNUNET_assert(cond)
Use this for fatal errors that cannot be handled.
GNUNET_SCHEDULER_TaskCallback error_cb
Function to call on errors.
Definition: namestore_api.c:92
struct GNUNET_NAMESTORE_QueueEntry * prev
Kept in a DLL.
Definition: namestore_api.c:62
uint32_t op_id
The operation id this zone iteration operation has.
Start a zone iteration for the given zone.
Definition: namestore.h:337
void * proc_cls
Closure for proc.
struct GNUNET_NAMESTORE_Header gns_header
Type will be GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_TO_NAME.
Definition: namestore.h:191
uint16_t name_len
Length of the name.
Definition: namestore.h:217
#define GNUNET_memcpy(dst, src, n)
Call memcpy() but check for n being 0 first.
#define GNUNET_MQ_hd_fixed_size(name, code, str, ctx)
void(* GNUNET_NAMESTORE_RecordMonitor)(void *cls, const struct GNUNET_CRYPTO_EcdsaPrivateKey *zone, const char *label, unsigned int rd_count, const struct GNUNET_GNSRECORD_Data *rd)
Process a record that was stored in the namestore.
static void handle_record_store_response(void *cls, const struct RecordStoreResponseMessage *msg)
Handle an incoming message of type GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_STORE_RESPONSE.
#define GNUNET_MQ_msg(mvar, type)
Allocate a GNUNET_MQ_Envelope.
Definition: gnunet_mq_lib.h:67
const struct GNUNET_CONFIGURATION_Handle * cfg
Configuration to use.
int16_t res
result in NBO: GNUNET_OK on success, GNUNET_NO if there were no results, GNUNET_SYSERR on error ...
Definition: namestore.h:233
#define GNUNET_NO
Definition: gnunet_common.h:78
#define GNUNET_OK
Named constants for return values.
Definition: gnunet_common.h:75
size_t data_size
Number of bytes in data.
#define GNUNET_new(type)
Allocate a struct or union of the given type.
void GNUNET_NAMESTORE_zone_iterator_next(struct GNUNET_NAMESTORE_ZoneIterator *it, uint64_t limit)
Calls the record processor specified in GNUNET_NAMESTORE_zone_iteration_start for the next record...
static void handle_record_result_end(void *cls, const struct GNUNET_NAMESTORE_Header *msg)
Handle an incoming message of type GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_RESULT_END.
Private ECC key encoded for transmission.
#define GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_RESULT_END
Service to client: end of list of results.
int GNUNET_GNSRECORD_records_deserialize(size_t len, const char *src, unsigned int rd_count, struct GNUNET_GNSRECORD_Data *dest)
Deserialize the given records to the given destination.
void * error_cb_cls
Closure for error_cb.
uint16_t size
The length of the struct (in bytes, including the length field itself), in big-endian format...
#define GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_LOOKUP
Client to service: lookup label.
void * proc_cls
Closure for proc.
Definition: namestore_api.c:87
void * error_cb_cls
Closure for error_cb.
Definition: namestore_api.c:97
#define GNUNET_GNSRECORD_TYPE_NICK
Record type for GNS nick names ("NICK").
#define GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_ITERATION_STOP
Client to service: stop iterating.
uint16_t reserved
always zero (for alignment)
Definition: namestore.h:86
#define GNUNET_break(cond)
Use this for internal assertion violations that are not fatal (can be handled) but should not occur...
uint32_t last_op_id_used
The last operation id used for a NAMESTORE operation.
void(* GNUNET_SCHEDULER_TaskCallback)(void *cls)
Signature of the main function of a task.
static int check_record_result(void *cls, const struct RecordResultMessage *msg)
Handle an incoming message of type GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_RESULT.
void GNUNET_NAMESTORE_cancel(struct GNUNET_NAMESTORE_QueueEntry *qe)
Cancel a namestore operation.
#define GNUNET_TIME_UNIT_FOREVER_ABS
Constant used to specify "forever".
#define _(String)
GNU gettext support macro.
Definition: platform.h:181
static void free_ze(struct GNUNET_NAMESTORE_ZoneIterator *ze)
Free ze.
struct GNUNET_NAMESTORE_QueueEntry * GNUNET_NAMESTORE_records_store(struct GNUNET_NAMESTORE_Handle *h, const struct GNUNET_CRYPTO_EcdsaPrivateKey *pkey, const char *label, unsigned int rd_count, const struct GNUNET_GNSRECORD_Data *rd, GNUNET_NAMESTORE_ContinuationWithStatus cont, void *cont_cls)
Store an item in the namestore.
uint16_t name_len
Name length.
Definition: namestore.h:259
common internal definitions for namestore service
static char * zone
Name of the zone we manage.
uint16_t rd_count
Number of records contained.
Definition: namestore.h:227
int32_t op_result
GNUNET_SYSERR on failure, GNUNET_OK on success
Definition: namestore.h:112
struct GNUNET_MessageHeader header
header.type will be GNUNET_MESSAGE_TYPE_NAMESTORE_* header.size will be message size ...
Definition: namestore.h:45
struct GNUNET_CRYPTO_EcdsaPrivateKey private_key
The private key of the authority.
Definition: namestore.h:279
void GNUNET_NAMESTORE_disconnect(struct GNUNET_NAMESTORE_Handle *h)
Disconnect from the namestore service (and free associated resources).
cryptographic primitives for GNUnet
struct GNUNET_CRYPTO_EcdsaPublicKey value_zone
The public key of the target zone.
Definition: namestore.h:201
#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
Handle for a zone iterator operation.
struct GNUNET_NAMESTORE_QueueEntry * next
Kept in a DLL.
Definition: namestore_api.c:57
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:1237
struct GNUNET_TIME_Relative reconnect_delay
Delay introduced before we reconnect.
static int check_rd(size_t rd_len, const void *rd_buf, unsigned int rd_count)
Check that rd_buf of lenght rd_len contains rd_count records.
uint16_t rd_len
Length of serialized record data.
Definition: namestore.h:76
const void * data
Binary value stored in the DNS record.
uint16_t rd_count
Number of records contained.
Definition: namestore.h:269
#define GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_STORE
Client to service: store records (as authority)
#define GNUNET_MQ_hd_var_size(name, code, str, ctx)
static void handle_record_result(void *cls, const struct RecordResultMessage *msg)
Handle an incoming message of type GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_RESULT.
Connection to the NAMESTORE service.
struct GNUNET_MQ_Handle * mq
Connection to the service (if available).
uint64_t expiration_time
Expiration time for the DNS record.
static void force_reconnect(struct GNUNET_NAMESTORE_Handle *h)
Disconnect from service and then reconnect.
static struct GNUNET_NAMESTORE_ZoneIterator * find_zi(struct GNUNET_NAMESTORE_Handle *h, uint32_t rid)
Find the zone iteration entry that matches the rid.
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:686
#define NAMESTORE_DELAY_TOLERANCE
We grant the namestore up to 1 minute of latency, if it is slower than that, store queries will fail...
Definition: namestore_api.c:47
Stop zone iteration for the given operation.
Definition: namestore.h:371
uint16_t name_len
Name length.
Definition: namestore.h:71
struct GNUNET_MQ_Envelope * env
Envelope of the message to send to the service, if not yet sent.
uint16_t name_len
Name length.
Definition: namestore.h:153
This is a private record of this peer and it should thus not be handed out to other peers...
void GNUNET_NAMESTORE_zone_iteration_stop(struct GNUNET_NAMESTORE_ZoneIterator *it)
Stops iteration and releases the namestore handle for further calls.
struct GNUNET_NAMESTORE_Header gns_header
Type will be GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_ITERATION_START.
Definition: namestore.h:341
Message handler for a specific message type.
static int res
static void warn_delay(void *cls)
Task launched to warn the user that the namestore is excessively slow and that a query was thus dropp...
uint16_t rd_count
Number of records contained.
Definition: namestore.h:81
static struct GNUNET_REVOCATION_Query * q
Handle for revocation query.
void GNUNET_MQ_discard(struct GNUNET_MQ_Envelope *mqm)
Discard the message queue message, free all allocated resources.
Definition: mq.c:319
#define GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_TO_NAME
Client to service: "reverse" lookup for zone name based on zone key.
static struct GNUNET_CONFIGURATION_Handle * cfg
Our configuration.
Definition: gnunet-arm.c:104
uint64_t GNUNET_htonll(uint64_t n)
Convert unsigned 64-bit integer to network byte order.
Definition: common_endian.c:35
struct GNUNET_NAMESTORE_QueueEntry * op_tail
Tail of pending namestore queue entries.
struct GNUNET_NAMESTORE_ZoneIterator * next
Kept in a DLL.
struct GNUNET_CRYPTO_EcdsaPrivateKey zone
The private key of the zone that contained the name.
Definition: namestore.h:238
#define GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_ITERATION_START
Client to service: please start iteration; receives "GNUNET_MESSAGE_TYPE_NAMESTORE_LOOKUP_NAME_RESPON...
#define GNUNET_SYSERR
Definition: gnunet_common.h:76
#define GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_ITERATION_NEXT
Client to service: next record(s) in iteration please.
An QueueEntry used to store information for a pending NAMESTORE record operation. ...
Definition: namestore_api.c:53
struct GNUNET_NAMESTORE_Handle * h
Main handle to access the namestore.
struct GNUNET_NAMESTORE_Handle * GNUNET_NAMESTORE_connect(const struct GNUNET_CONFIGURATION_Handle *cfg)
Initialize the connection with the NAMESTORE service.
const char * name
struct GNUNET_NAMESTORE_ZoneIterator * prev
Kept in a DLL.
uint32_t op_id
The operation id this zone iteration operation has.
#define GNUNET_CONTAINER_DLL_insert_tail(head, tail, element)
Insert an element at the tail of a DLL.
uint16_t found
Was the label found in the database?? GNUNET_YES or GNUNET_NO.
Definition: namestore.h:169
uint16_t rd_len
Length of serialized record data.
Definition: namestore.h:264
#define GNUNET_TIME_STD_BACKOFF(r)
Perform our standard exponential back-off calculation, starting at 1 ms and then going by a factor of...
GNUNET_NAMESTORE_ContinuationWithStatus cont
Continuation to call.
Definition: namestore_api.c:72
static void reconnect(struct GNUNET_NAMESTORE_Handle *h)
Reconnect to namestore service.
struct GNUNET_NAMESTORE_Header gns_header
Type will be GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_RESULT.
Definition: namestore.h:254
#define GNUNET_memcmp(a, b)
Compare memory in a and b, where both must be of the same pointer type.
static void free_qe(struct GNUNET_NAMESTORE_QueueEntry *qe)
Free qe.
#define GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_LOOKUP_RESPONSE
Service to client: lookup label.
int reconnect
Should we reconnect to service due to some serious error?
#define LOG(kind,...)
Definition: namestore_api.c:41
Handle to a message queue.
Definition: mq.c:84
struct GNUNET_NAMESTORE_Header gns_header
Type will be GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_TO_NAME_RESPONSE.
Definition: namestore.h:212
struct GNUNET_CRYPTO_EcdsaPrivateKey private_key
The private key of the authority.
Definition: namestore.h:91
void * finish_cb_cls
Closure for error_cb.
Store a record to the namestore (as authority).
Definition: namestore.h:57
Respone for zone to name lookup.
Definition: namestore.h:208
void * cont_cls
Closure for cont.
Definition: namestore_api.c:77
struct GNUNET_CRYPTO_EcdsaPrivateKey zone
The private key of the zone to look up in.
Definition: namestore.h:196
struct GNUNET_NAMESTORE_Header gns_header
Type will be GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_LOOKUP_RESPONSE.
Definition: namestore.h:148
uint32_t record_type
Type of the GNS/DNS record.
configuration data
Definition: configuration.c:83
Response to a record storage request.
Definition: namestore.h:103
struct GNUNET_NAMESTORE_QueueEntry * op_head
Head of pending namestore queue entries.
Public ECC key (always for Curve25519) encoded in a format suitable for network transmission and ECDS...
struct GNUNET_NAMESTORE_ZoneIterator * z_head
Head of pending namestore zone iterator entries.
#define MAX_NAME_LEN
Maximum length of any name, including 0-termination.
Definition: namecache.h:33
static uint32_t get_op_id(struct GNUNET_NAMESTORE_Handle *h)
Get a fresh operation id to distinguish between namestore requests.
struct GNUNET_NAMESTORE_QueueEntry * GNUNET_NAMESTORE_zone_to_name(struct GNUNET_NAMESTORE_Handle *h, const struct GNUNET_CRYPTO_EcdsaPrivateKey *zone, const struct GNUNET_CRYPTO_EcdsaPublicKey *value_zone, GNUNET_SCHEDULER_TaskCallback error_cb, void *error_cb_cls, GNUNET_NAMESTORE_RecordMonitor proc, void *proc_cls)
Look for an existing PKEY delegation record for a given public key.
#define GNUNET_log(kind,...)
struct GNUNET_CRYPTO_EcdsaPrivateKey private_key
The private key of the authority.
Definition: namestore.h:174
Entry in list of pending tasks.
Definition: scheduler.c:131
Generic namestore message with op id.
Definition: namestore.h:40
static void handle_zone_to_name_response(void *cls, const struct ZoneToNameResponseMessage *msg)
Handle an incoming message of type GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_TO_NAME_RESPONSE.
struct GNUNET_SCHEDULER_Task * timeout_task
Task scheduled to warn us if the namestore is way too slow.
uint16_t rd_len
Length of serialized record data.
Definition: namestore.h:222
struct GNUNET_NAMESTORE_Header gns_header
Type will be GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_LOOKUP.
Definition: namestore.h:123
Lookup a name for a zone hash.
Definition: namestore.h:187
Lookup a label.
Definition: namestore.h:119
struct GNUNET_SCHEDULER_Task * reconnect_task
Reconnect task.
void GNUNET_MQ_destroy(struct GNUNET_MQ_Handle *mq)
Destroy the message queue.
Definition: mq.c:821
#define GNUNET_YES
Definition: gnunet_common.h:77
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:351
#define GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_RESULT
Service to client: here is a (plaintext) record you requested.
struct GNUNET_NAMESTORE_ZoneIterator * z_tail
Tail of pending namestore zone iterator entries.
Record is returned from the namestore (as authority).
Definition: namestore.h:250
uint64_t limit
Number of records to return to the iterator in one shot (before GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_IT...
Definition: namestore.h:364
enum GNUNET_GNSRECORD_Flags flags
Flags for the record.
static struct GNUNET_NAMESTORE_QueueEntry * find_qe(struct GNUNET_NAMESTORE_Handle *h, uint32_t rid)
Find the queue entry that matches the rid.
static void mq_error_handler(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_NAMESTORE_QueueEntry * GNUNET_NAMESTORE_set_nick(struct GNUNET_NAMESTORE_Handle *h, const struct GNUNET_CRYPTO_EcdsaPrivateKey *pkey, const char *nick, GNUNET_NAMESTORE_ContinuationWithStatus cont, void *cont_cls)
Set the desired nick name for a zone.
struct GNUNET_CRYPTO_EcdsaPrivateKey zone
Zone key.
Definition: namestore.h:346
struct GNUNET_NAMESTORE_Header gns_header
Type will be GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_ITERATION_NEXT.
Definition: namestore.h:357
#define GNUNET_MQ_handler_end()
End-marker for the handlers array.
struct GNUNET_NAMESTORE_Header gns_header
Type will be GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_ITERATION_STOP.
Definition: namestore.h:375
Lookup a label.
Definition: namestore.h:144
static int check_lookup_result(void *cls, const struct LabelLookupResponseMessage *msg)
Check validity of an incoming message of type GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_LOOKUP_RESPONSE.
struct GNUNET_CRYPTO_EcdsaPrivateKey zone
The private key of the zone to look up in.
Definition: namestore.h:133
static void reconnect_task(void *cls)
Re-establish the connection to the service.
#define GNUNET_free(ptr)
Wrapper around free.
Time for relative time used by GNUnet, in microseconds.
void * GNUNET_SCHEDULER_cancel(struct GNUNET_SCHEDULER_Task *task)
Cancel the task with the specified identifier.
Definition: scheduler.c:956
#define GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_STORE_RESPONSE
Service to client: result of store operation.
struct GNUNET_CRYPTO_EcdsaPrivateKey zone
Private key of the zone.