2 This file is part of GNUnet.
3 (C) 2009, 2010 Christian Grothoff (and other contributing authors)
5 GNUnet is free software; you can redistribute it and/or modify
6 it under the terms of the GNU General Public License as published
7 by the Free Software Foundation; either version 3, or (at your
8 option) any later version.
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 General Public License for more details.
15 You should have received a copy of the GNU General Public License
16 along with GNUnet; see the file COPYING. If not, write to the
17 Free Software Foundation, Inc., 59 Temple Place - Suite 330,
18 Boston, MA 02111-1307, USA.
22 * @file namestore/namestore_api.c
23 * @brief API to access the NAMESTORE service
24 * @author Martin Schanzenbach
25 * @author Matthias Wachs
29 #include "gnunet_util_lib.h"
30 #include "gnunet_crypto_lib.h"
31 #include "gnunet_constants.h"
32 #include "gnunet_dnsparser_lib.h"
33 #include "gnunet_arm_service.h"
34 #include "gnunet_signatures.h"
35 #include "gnunet_namestore_service.h"
36 #include "namestore.h"
38 #define DEBUG_GNS_API GNUNET_EXTRA_LOGGING
40 #define LOG(kind,...) GNUNET_log_from (kind, "gns-api",__VA_ARGS__)
45 struct GNUNET_NAMESTORE_QueueEntry
51 struct GNUNET_NAMESTORE_QueueEntry *next;
56 struct GNUNET_NAMESTORE_QueueEntry *prev;
58 struct GNUNET_NAMESTORE_Handle *nsh;
62 GNUNET_NAMESTORE_ContinuationWithStatus cont;
65 GNUNET_NAMESTORE_RecordProcessor proc;
68 char *data; /*stub data pointer*/
75 struct GNUNET_NAMESTORE_ZoneIterator
81 struct GNUNET_NAMESTORE_ZoneIterator *next;
86 struct GNUNET_NAMESTORE_ZoneIterator *prev;
90 struct GNUNET_NAMESTORE_Handle *h;
91 GNUNET_NAMESTORE_RecordProcessor proc;
100 * Message in linked list we should send to the service. The
101 * actual binary message follows this struct.
103 struct PendingMessage
109 struct PendingMessage *next;
114 struct PendingMessage *prev;
117 * Size of the message.
122 * Is this the 'START' message?
129 * Connection to the NAMESTORE service.
131 struct GNUNET_NAMESTORE_Handle
135 * Configuration to use.
137 const struct GNUNET_CONFIGURATION_Handle *cfg;
140 * Socket (if available).
142 struct GNUNET_CLIENT_Connection *client;
145 * Currently pending transmission request (or NULL).
147 struct GNUNET_CLIENT_TransmitHandle *th;
152 GNUNET_SCHEDULER_TaskIdentifier reconnect_task;
155 * Pending messages to send to the service
158 struct PendingMessage * pending_head;
159 struct PendingMessage * pending_tail;
162 * Should we reconnect to service due to some serious error?
168 * Pending namestore queue entries
170 struct GNUNET_NAMESTORE_QueueEntry * op_head;
171 struct GNUNET_NAMESTORE_QueueEntry * op_tail;
176 * Pending namestore zone iterator entries
178 struct GNUNET_NAMESTORE_ZoneIterator * z_head;
179 struct GNUNET_NAMESTORE_ZoneIterator * z_tail;
182 struct GNUNET_NAMESTORE_SimpleRecord
187 struct GNUNET_NAMESTORE_SimpleRecord *next;
192 struct GNUNET_NAMESTORE_SimpleRecord *prev;
195 const GNUNET_HashCode *zone;
196 uint32_t record_type;
197 struct GNUNET_TIME_Absolute expiration;
198 enum GNUNET_NAMESTORE_RecordFlags flags;
206 * Convert a type name (i.e. "AAAA") to the corresponding number.
208 * @param typename name to convert
209 * @return corresponding number, UINT32_MAX on error
212 GNUNET_NAMESTORE_typename_to_number (const char *typename)
218 { "A", GNUNET_DNSPARSER_TYPE_A },
219 { "NS", GNUNET_DNSPARSER_TYPE_NS },
220 { "CNAME", GNUNET_DNSPARSER_TYPE_CNAME },
221 { "SOA", GNUNET_DNSPARSER_TYPE_SOA },
222 { "PTR", GNUNET_DNSPARSER_TYPE_PTR },
223 { "MX", GNUNET_DNSPARSER_TYPE_MX },
224 { "TXT", GNUNET_DNSPARSER_TYPE_TXT },
225 { "AAAA", GNUNET_DNSPARSER_TYPE_AAAA },
226 { "PKEY", GNUNET_NAMESTORE_TYPE_PKEY },
227 { "PSEU", GNUNET_NAMESTORE_TYPE_PSEU },
233 while ( (map[i].name != NULL) &&
234 (0 != strcasecmp (typename, map[i].name)) )
236 return map[i].number;
241 * Disconnect from service and then reconnect.
243 * @param h our handle
246 force_reconnect (struct GNUNET_NAMESTORE_Handle *h);
249 handle_lookup_name_response (struct GNUNET_NAMESTORE_QueueEntry *qe,
250 struct LookupNameResponseMessage * msg,
253 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received `%s' \n",
254 "LOOKUP_NAME_RESPONSE");
256 struct GNUNET_NAMESTORE_Handle *h = qe->nsh;
257 struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key;
261 struct GNUNET_CRYPTO_RsaSignature *signature = NULL;
262 struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded dummy;
263 struct GNUNET_TIME_Absolute expire;
268 int contains_sig = GNUNET_NO;
271 rd_len = ntohs (msg->rd_len);
272 rd_count = ntohs (msg->rd_count);
273 msg_len = ntohs (msg->gns_header.header.size);
274 name_len = ntohs (msg->name_len);
275 contains_sig = ntohs (msg->contains_sig);
276 expire = GNUNET_TIME_absolute_ntoh(msg->expire);
278 exp_msg_len = sizeof (struct LookupNameResponseMessage) +
279 sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded) +
282 contains_sig * sizeof (struct GNUNET_CRYPTO_RsaSignature);
284 if (msg_len != exp_msg_len)
286 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Message size describes with `%u' bytes but calculated size is %u bytes \n",
287 msg_len, exp_msg_len);
292 zone_key = (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *) &msg[1];
293 name = (char *) &zone_key[1];
294 rd_tmp = &name[name_len];
296 struct GNUNET_NAMESTORE_RecordData rd[rd_count];
297 GNUNET_NAMESTORE_records_deserialize(rd_len, rd_tmp, rd_count, rd);
299 /* reset values if values not contained */
300 if (contains_sig == GNUNET_NO)
303 signature = (struct GNUNET_CRYPTO_RsaSignature *) &rd_tmp[rd_len];
307 memset (&dummy, '0', sizeof(struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded));
308 if (0 == memcmp (zone_key, &dummy, sizeof(struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded)))
311 if (qe->proc != NULL)
313 qe->proc (qe->proc_cls, zone_key, expire, name, rd_count, (rd_count > 0) ? rd : NULL, signature);
316 /* Operation done, remove */
317 GNUNET_CONTAINER_DLL_remove(h->op_head, h->op_tail, qe);
323 handle_record_put_response (struct GNUNET_NAMESTORE_QueueEntry *qe,
324 struct RecordPutResponseMessage* msg,
327 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received `%s' \n",
328 "RECORD_PUT_RESPONSE");
330 struct GNUNET_NAMESTORE_Handle *h = qe->nsh;
333 if (ntohs (msg->op_result) == GNUNET_OK)
336 if (qe->cont != NULL)
338 qe->cont (qe->cont_cls, res, _("Namestore added record successfully"));
342 else if (ntohs (msg->op_result) == GNUNET_NO)
345 if (qe->cont != NULL)
347 qe->cont (qe->cont_cls, res, _("Namestore failed to add record"));
356 /* Operation done, remove */
357 GNUNET_CONTAINER_DLL_remove(h->op_head, h->op_tail, qe);
364 handle_record_create_response (struct GNUNET_NAMESTORE_QueueEntry *qe,
365 struct RecordCreateResponseMessage* msg,
368 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received `%s' \n",
369 "RECORD_CREATE_RESPONSE");
371 struct GNUNET_NAMESTORE_Handle *h = qe->nsh;
373 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received `%s' %i\n",
374 "RECORD_CREATE_RESPONSE", ntohs (msg->op_result));
375 if (ntohs (msg->op_result) == GNUNET_YES)
377 if (qe->cont != NULL)
379 qe->cont (qe->cont_cls, GNUNET_YES, _("Namestore added record successfully"));
383 else if (ntohs (msg->op_result) == GNUNET_NO)
385 if (qe->cont != NULL)
387 qe->cont (qe->cont_cls, GNUNET_NO, _("Namestore record already existed"));
392 if (qe->cont != NULL)
394 qe->cont (qe->cont_cls, GNUNET_SYSERR, _("Namestore failed to add record\n"));
398 /* Operation done, remove */
399 GNUNET_CONTAINER_DLL_remove(h->op_head, h->op_tail, qe);
406 handle_record_remove_response (struct GNUNET_NAMESTORE_QueueEntry *qe,
407 struct RecordRemoveResponseMessage* msg,
410 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received `%s' \n",
411 "RECORD_REMOVE_RESPONSE");
413 struct GNUNET_NAMESTORE_Handle *h = qe->nsh;
414 int res = ntohs (msg->op_result);
419 * 1 : No records for entry
420 * 2 : Could not find record to remove
421 * 3 : Failed to create new signature
422 * 4 : Failed to put new set of records in database
426 if (qe->cont != NULL)
428 qe->cont (qe->cont_cls, GNUNET_YES, _("Namestore removed record successfully"));
433 if (qe->cont != NULL)
435 qe->cont (qe->cont_cls, GNUNET_NO, _("No records for entry"));
440 if (qe->cont != NULL)
442 qe->cont (qe->cont_cls, GNUNET_NO, _("Could not find record to remove"));
447 if (qe->cont != NULL)
449 qe->cont (qe->cont_cls, GNUNET_SYSERR, _("Failed to create new signature"));
454 if (qe->cont != NULL)
456 qe->cont (qe->cont_cls, GNUNET_SYSERR, _("Failed to put new set of records in database"));
464 /* Operation done, remove */
465 GNUNET_CONTAINER_DLL_remove(h->op_head, h->op_tail, qe);
471 handle_zone_to_name_response (struct GNUNET_NAMESTORE_QueueEntry *qe,
472 struct ZoneToNameResponseMessage* msg,
475 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received `%s' \n",
476 "ZONE_TO_NAME_RESPONSE");
478 struct GNUNET_NAMESTORE_Handle *h = qe->nsh;
479 int res = ntohs (msg->res);
481 struct GNUNET_TIME_Absolute expire;
484 unsigned int rd_count;
489 struct GNUNET_CRYPTO_RsaSignature* sig_tmp;
491 if (res == GNUNET_SYSERR)
493 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "An error occured during zone to name operation\n");
494 if (qe->proc != NULL)
495 qe->proc (qe->proc_cls, NULL, GNUNET_TIME_absolute_get_zero(), NULL, 0, NULL, NULL);
497 else if (res == GNUNET_NO)
499 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Namestore has no result for zone to name mapping \n");
500 if (qe->proc != NULL)
501 qe->proc (qe->proc_cls, NULL, GNUNET_TIME_absolute_get_zero(), NULL, 0, NULL, NULL);
503 else if (res == GNUNET_YES)
505 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Namestore has result for zone to name mapping \n");
507 name_len = ntohs (msg->name_len);
508 rd_count = ntohs (msg->rd_count);
509 rd_ser_len = ntohs (msg->rd_len);
510 have_signature = ntohl (msg->contains_sig);
511 expire = GNUNET_TIME_absolute_ntoh(msg->expire);
513 name_tmp = (char *) &msg[1];
514 rd_tmp = &name_tmp[name_len];
515 if (have_signature == GNUNET_YES)
516 sig_tmp = (struct GNUNET_CRYPTO_RsaSignature *) &rd_tmp[rd_ser_len];
520 struct GNUNET_NAMESTORE_RecordData rd[rd_count];
521 GNUNET_NAMESTORE_records_deserialize(rd_ser_len, rd_tmp, rd_count, rd);
523 if (qe->proc != NULL)
524 qe->proc (qe->proc_cls, &msg->zone_key, expire, name_tmp, rd_count, rd, sig_tmp);
530 /* Operation done, remove */
531 GNUNET_CONTAINER_DLL_remove(h->op_head, h->op_tail, qe);
537 manage_record_operations (struct GNUNET_NAMESTORE_QueueEntry *qe,
538 const struct GNUNET_MessageHeader *msg,
539 int type, size_t size)
542 /* handle different message type */
544 case GNUNET_MESSAGE_TYPE_NAMESTORE_LOOKUP_NAME_RESPONSE:
545 if (size < sizeof (struct LookupNameResponseMessage))
550 handle_lookup_name_response (qe, (struct LookupNameResponseMessage *) msg, size);
552 case GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_PUT_RESPONSE:
553 if (size != sizeof (struct RecordPutResponseMessage))
558 handle_record_put_response (qe, (struct RecordPutResponseMessage *) msg, size);
560 case GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_CREATE_RESPONSE:
561 if (size != sizeof (struct RecordCreateResponseMessage))
566 handle_record_create_response (qe, (struct RecordCreateResponseMessage *) msg, size);
568 case GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_REMOVE_RESPONSE:
569 if (size != sizeof (struct RecordRemoveResponseMessage))
574 handle_record_remove_response (qe, (struct RecordRemoveResponseMessage *) msg, size);
576 case GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_TO_NAME_RESPONSE:
577 if (size < sizeof (struct ZoneToNameResponseMessage))
582 handle_zone_to_name_response (qe, (struct ZoneToNameResponseMessage *) msg, size);
591 handle_zone_iteration_response (struct GNUNET_NAMESTORE_ZoneIterator *ze,
592 struct ZoneIterationResponseMessage *msg,
595 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received `%s' \n",
596 "ZONE_ITERATION_RESPONSE");
599 if (ze->proc != NULL)
602 ze->proc(ze->proc_cls, NULL, GNUNET_TIME_absolute_get_forever(), "dummy", 0, NULL, NULL);
608 manage_zone_operations (struct GNUNET_NAMESTORE_ZoneIterator *ze,
609 const struct GNUNET_MessageHeader *msg,
610 int type, size_t size)
613 /* handle different message type */
615 case GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_ITERATION_RESPONSE:
616 if (size < sizeof (struct ZoneIterationResponseMessage))
621 handle_zone_iteration_response (ze, (struct ZoneIterationResponseMessage *) msg, size);
630 * Type of a function to call when we receive a message
633 * @param cls the 'struct GNUNET_NAMESTORE_SchedulingHandle'
634 * @param msg message received, NULL on timeout or fatal error
637 process_namestore_message (void *cls, const struct GNUNET_MessageHeader *msg)
639 struct GNUNET_NAMESTORE_Handle *h = cls;
640 struct GNUNET_NAMESTORE_Header * gm;
641 struct GNUNET_NAMESTORE_QueueEntry *qe;
642 struct GNUNET_NAMESTORE_ZoneIterator *ze;
645 uint32_t r_id = UINT32_MAX;
653 size = ntohs (msg->size);
654 type = ntohs (msg->type);
656 if (size < sizeof (struct GNUNET_NAMESTORE_Header))
659 GNUNET_CLIENT_receive (h->client, &process_namestore_message, h,
660 GNUNET_TIME_UNIT_FOREVER_REL);
664 gm = (struct GNUNET_NAMESTORE_Header *) msg;
665 r_id = ntohl (gm->r_id);
667 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received message type %i size %i op %u\n", type, size, r_id);
669 /* Find matching operation */
672 /* No matching pending operation found */
674 GNUNET_CLIENT_receive (h->client, &process_namestore_message, h,
675 GNUNET_TIME_UNIT_FOREVER_REL);
679 /* Is it a record related operation ? */
680 for (qe = h->op_head; qe != NULL; qe = qe->next)
682 if (qe->op_id == r_id)
687 manage_record_operations (qe, msg, type, size);
690 /* Is it a zone iteration operation ? */
691 for (ze = h->z_head; ze != NULL; ze = ze->next)
693 if (ze->op_id == r_id)
698 manage_zone_operations (ze, msg, type, size);
701 GNUNET_CLIENT_receive (h->client, &process_namestore_message, h,
702 GNUNET_TIME_UNIT_FOREVER_REL);
704 if (GNUNET_YES == h->reconnect)
711 * Transmit messages from the message queue to the service
712 * (if there are any, and if we are not already trying).
714 * @param h handle to use
717 do_transmit (struct GNUNET_NAMESTORE_Handle *h);
721 * We can now transmit a message to NAMESTORE. Do it.
723 * @param cls the 'struct GNUNET_NAMESTORE_Handle'
724 * @param size number of bytes we can transmit
725 * @param buf where to copy the messages
726 * @return number of bytes copied into buf
729 transmit_message_to_namestore (void *cls, size_t size, void *buf)
731 struct GNUNET_NAMESTORE_Handle *h = cls;
732 struct PendingMessage *p;
737 if ((size == 0) || (buf == NULL))
744 while ((NULL != (p = h->pending_head)) && (p->size <= size))
746 memcpy (&cbuf[ret], &p[1], p->size);
749 GNUNET_CONTAINER_DLL_remove (h->pending_head, h->pending_tail, p);
750 if (GNUNET_YES == p->is_init)
751 GNUNET_CLIENT_receive (h->client, &process_namestore_message, h,
752 GNUNET_TIME_UNIT_FOREVER_REL);
761 * Transmit messages from the message queue to the service
762 * (if there are any, and if we are not already trying).
764 * @param h handle to use
767 do_transmit (struct GNUNET_NAMESTORE_Handle *h)
769 struct PendingMessage *p;
773 if (NULL == (p = h->pending_head))
775 if (NULL == h->client)
776 return; /* currently reconnecting */
778 h->th = GNUNET_CLIENT_notify_transmit_ready (h->client, p->size,
779 GNUNET_TIME_UNIT_FOREVER_REL,
780 GNUNET_NO, &transmit_message_to_namestore,
786 * Reconnect to namestore service.
788 * @param h the handle to the namestore service
791 reconnect (struct GNUNET_NAMESTORE_Handle *h)
793 struct PendingMessage *p;
794 struct StartMessage *init;
796 GNUNET_assert (NULL == h->client);
797 h->client = GNUNET_CLIENT_connect ("namestore", h->cfg);
798 GNUNET_assert (NULL != h->client);
800 if ((NULL == (p = h->pending_head)) || (GNUNET_YES != p->is_init))
802 p = GNUNET_malloc (sizeof (struct PendingMessage) +
803 sizeof (struct StartMessage));
804 p->size = sizeof (struct StartMessage);
805 p->is_init = GNUNET_YES;
806 init = (struct StartMessage *) &p[1];
807 init->header.type = htons (GNUNET_MESSAGE_TYPE_NAMESTORE_START);
808 init->header.size = htons (sizeof (struct StartMessage));
809 GNUNET_CONTAINER_DLL_insert (h->pending_head, h->pending_tail, p);
815 * Re-establish the connection to the service.
817 * @param cls handle to use to re-connect.
818 * @param tc scheduler context
821 reconnect_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc)
823 struct GNUNET_NAMESTORE_Handle *h = cls;
825 h->reconnect_task = GNUNET_SCHEDULER_NO_TASK;
831 * Disconnect from service and then reconnect.
833 * @param h our handle
836 force_reconnect (struct GNUNET_NAMESTORE_Handle *h)
838 h->reconnect = GNUNET_NO;
839 GNUNET_CLIENT_disconnect (h->client, GNUNET_NO);
841 h->reconnect_task = GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_SECONDS,
847 get_op_id (struct GNUNET_NAMESTORE_Handle *h)
849 uint32_t op_id = h->op_id;
855 * Initialize the connection with the NAMESTORE service.
857 * @param cfg configuration to use
858 * @return handle to the GNS service, or NULL on error
860 struct GNUNET_NAMESTORE_Handle *
861 GNUNET_NAMESTORE_connect (const struct GNUNET_CONFIGURATION_Handle *cfg)
863 struct GNUNET_NAMESTORE_Handle *h;
865 h = GNUNET_malloc (sizeof (struct GNUNET_NAMESTORE_Handle));
867 h->reconnect_task = GNUNET_SCHEDULER_add_now (&reconnect_task, h);
872 struct DisconnectContext
874 struct GNUNET_NAMESTORE_Handle *h;
879 clean_up_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc)
881 struct PendingMessage *p;
882 struct GNUNET_NAMESTORE_QueueEntry *q;
883 struct GNUNET_NAMESTORE_ZoneIterator *z;
884 struct GNUNET_NAMESTORE_Handle *h = cls;
885 GNUNET_assert (h != NULL);
886 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Cleaning up\n");
887 while (NULL != (p = h->pending_head))
889 GNUNET_CONTAINER_DLL_remove (h->pending_head, h->pending_tail, p);
893 while (NULL != (q = h->op_head))
896 GNUNET_CONTAINER_DLL_remove (h->op_head, h->op_tail, q);
900 while (NULL != (z = h->z_head))
902 GNUNET_CONTAINER_DLL_remove (h->z_head, h->z_tail, z);
906 if (NULL != h->client)
908 GNUNET_CLIENT_disconnect (h->client, GNUNET_NO);
911 if (GNUNET_SCHEDULER_NO_TASK != h->reconnect_task)
913 GNUNET_SCHEDULER_cancel (h->reconnect_task);
914 h->reconnect_task = GNUNET_SCHEDULER_NO_TASK;
921 transmit_disconnect_to_namestore (void *cls, size_t size, void *buf)
923 struct DisconnectContext * d_ctx = cls;
924 struct DisconnectMessage d_msg;
925 struct GNUNET_NAMESTORE_Handle *h = d_ctx->h;
928 d_msg.header.type = htons (GNUNET_MESSAGE_TYPE_NAMESTORE_DISCONNECT);
929 d_msg.header.size = htons (sizeof (struct DisconnectMessage));
930 d_msg.drop = htonl (d_ctx->drop);
933 if ((size == 0) || (buf == NULL) || (size < sizeof (struct DisconnectMessage)))
940 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending `%s' message to service \n", "NAMESTORE_DISCONNECT");
941 memcpy (buf, &d_msg, sizeof (struct DisconnectMessage));
942 res = sizeof (struct DisconnectMessage);
945 GNUNET_SCHEDULER_add_now (&clean_up_task, h);
951 * Disconnect from the namestore service (and free associated
954 * @param h handle to the namestore
955 * @param drop set to GNUNET_YES to delete all data in namestore (!)
958 GNUNET_NAMESTORE_disconnect (struct GNUNET_NAMESTORE_Handle *h, int drop)
962 GNUNET_CLIENT_notify_transmit_ready_cancel(h->th);
965 if (h->client != NULL)
967 struct DisconnectContext *d_ctx = GNUNET_malloc (sizeof (struct DisconnectContext));
971 h->th = GNUNET_CLIENT_notify_transmit_ready (h->client, sizeof (struct DisconnectMessage),
972 GNUNET_TIME_UNIT_FOREVER_REL,
973 GNUNET_NO, &transmit_disconnect_to_namestore,
978 GNUNET_log (GNUNET_ERROR_TYPE_WARNING, "Could not send disconnect notification to namestore service, we are not connected!\n");
979 if (GNUNET_YES == drop)
980 GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "NAMESTORE will not drop content\n");
981 GNUNET_SCHEDULER_add_now (&clean_up_task, h);
987 * Store an item in the namestore. If the item is already present,
988 * the expiration time is updated to the max of the existing time and
989 * the new time. This API is used when we cache signatures from other
992 * @param h handle to the namestore
993 * @param zone_key public key of the zone
994 * @param name name that is being mapped (at most 255 characters long)
995 * @param expire when does the corresponding block in the DHT expire (until
996 * when should we never do a DHT lookup for the same name again)?
997 * @param rd_count number of entries in 'rd' array
998 * @param rd array of records with data to store
999 * @param signature signature for all the records in the zone under the given name
1000 * @param cont continuation to call when done
1001 * @param cont_cls closure for cont
1002 * @return handle to abort the request
1004 struct GNUNET_NAMESTORE_QueueEntry *
1005 GNUNET_NAMESTORE_record_put (struct GNUNET_NAMESTORE_Handle *h,
1006 const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key,
1008 struct GNUNET_TIME_Absolute expire,
1009 unsigned int rd_count,
1010 const struct GNUNET_NAMESTORE_RecordData *rd,
1011 const struct GNUNET_CRYPTO_RsaSignature *signature,
1012 GNUNET_NAMESTORE_ContinuationWithStatus cont,
1015 struct GNUNET_NAMESTORE_QueueEntry *qe;
1016 struct PendingMessage *pe;
1018 /* pointer to elements */
1019 char * zone_key_tmp;
1023 size_t msg_size = 0;
1024 size_t name_len = 0;
1025 size_t rd_ser_len = 0;
1026 size_t pubkey_len = 0;
1029 GNUNET_assert (NULL != h);
1030 GNUNET_assert (NULL != zone_key);
1031 GNUNET_assert (NULL != name);
1032 GNUNET_assert (NULL != rd);
1033 GNUNET_assert (NULL != signature);
1035 name_len = strlen(name) + 1;
1043 qe = GNUNET_malloc(sizeof (struct GNUNET_NAMESTORE_QueueEntry));
1046 qe->cont_cls = cont_cls;
1048 GNUNET_CONTAINER_DLL_insert_tail(h->op_head, h->op_tail, qe);
1051 rd_ser_len = GNUNET_NAMESTORE_records_get_size(rd_count, rd);
1052 char rd_ser[rd_ser_len];
1053 GNUNET_NAMESTORE_records_serialize(rd_count, rd, rd_ser_len, rd_ser);
1055 pubkey_len = sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded);
1056 struct RecordPutMessage * msg;
1057 msg_size = sizeof (struct RecordPutMessage) + pubkey_len + name_len + rd_ser_len;
1059 /* create msg here */
1060 pe = GNUNET_malloc(sizeof (struct PendingMessage) + msg_size);
1061 pe->size = msg_size;
1062 pe->is_init = GNUNET_NO;
1063 msg = (struct RecordPutMessage *) &pe[1];
1064 zone_key_tmp = (char *) &msg[1];
1065 name_tmp = (char *) &zone_key_tmp[pubkey_len];
1066 rd_tmp = &name_tmp[name_len];
1068 msg->gns_header.header.type = htons (GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_PUT);
1069 msg->gns_header.header.size = htons (msg_size);
1070 msg->gns_header.r_id = htonl (rid);
1071 msg->key_len = htons (pubkey_len);
1072 memcpy (zone_key_tmp, zone_key, pubkey_len);
1073 msg->signature = *signature;
1074 msg->name_len = htons (name_len);
1075 memcpy (name_tmp, name, name_len);
1076 msg->expire = GNUNET_TIME_absolute_hton (expire);
1077 msg->rd_len = htons (rd_ser_len);
1078 msg->rd_count = htons (rd_count);
1080 memcpy (rd_tmp, rd_ser, rd_ser_len);
1082 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending `%s' message for name `%s' with size %u\n", "NAMESTORE_RECORD_PUT", name, msg_size);
1084 GNUNET_CONTAINER_DLL_insert_tail (h->pending_head, h->pending_tail, pe);
1092 * Check if a signature is valid. This API is used by the GNS Block
1093 * to validate signatures received from the network.
1095 * @param public_key public key of the zone
1096 * @param name name that is being mapped (at most 255 characters long)
1097 * @param rd_count number of entries in 'rd' array
1098 * @param rd array of records with data to store
1099 * @param signature signature for all the records in the zone under the given name
1100 * @return GNUNET_OK if the signature is valid
1103 GNUNET_NAMESTORE_verify_signature (const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *public_key,
1105 unsigned int rd_count,
1106 const struct GNUNET_NAMESTORE_RecordData *rd,
1107 const struct GNUNET_CRYPTO_RsaSignature *signature)
1109 int res = GNUNET_SYSERR;
1110 size_t rd_ser_len = 0;
1111 size_t name_len = 0;
1114 struct GNUNET_CRYPTO_RsaSignaturePurpose *sig_purpose;
1116 GNUNET_assert (public_key != NULL);
1117 GNUNET_assert (name != NULL);
1118 GNUNET_assert (signature != NULL);
1120 rd_ser_len = GNUNET_NAMESTORE_records_get_size(rd_count, rd);
1121 char rd_ser[rd_ser_len];
1122 GNUNET_NAMESTORE_records_serialize(rd_count, rd, rd_ser_len, rd_ser);
1124 name_len = strlen (name) + 1;
1126 sig_purpose = GNUNET_malloc(sizeof (struct GNUNET_CRYPTO_RsaSignaturePurpose) + rd_ser_len + name_len);
1127 sig_purpose->size = htonl (sizeof (struct GNUNET_CRYPTO_RsaSignaturePurpose)+ rd_ser_len + name_len);
1128 sig_purpose->purpose = htonl (GNUNET_SIGNATURE_PURPOSE_GNS_RECORD_SIGN);
1129 name_tmp = (char *) &sig_purpose[1];
1130 rd_tmp = &name_tmp[name_len];
1131 memcpy (name_tmp, name, name_len);
1132 memcpy (rd_tmp, rd_ser, rd_ser_len);
1134 res = GNUNET_CRYPTO_rsa_verify(GNUNET_SIGNATURE_PURPOSE_GNS_RECORD_SIGN, sig_purpose, signature, public_key);
1136 GNUNET_free (sig_purpose);
1142 * Store an item in the namestore. If the item is already present,
1143 * the expiration time is updated to the max of the existing time and
1144 * the new time. This API is used by the authority of a zone.
1146 * @param h handle to the namestore
1147 * @param pkey private key of the zone
1148 * @param name name that is being mapped (at most 255 characters long)
1149 * @param rd record data to store
1150 * @param cont continuation to call when done
1151 * @param cont_cls closure for cont
1152 * @return handle to abort the request
1154 struct GNUNET_NAMESTORE_QueueEntry *
1155 GNUNET_NAMESTORE_record_create (struct GNUNET_NAMESTORE_Handle *h,
1156 const struct GNUNET_CRYPTO_RsaPrivateKey *pkey,
1158 const struct GNUNET_NAMESTORE_RecordData *rd,
1159 GNUNET_NAMESTORE_ContinuationWithStatus cont,
1162 struct GNUNET_NAMESTORE_QueueEntry *qe;
1163 struct PendingMessage *pe;
1167 size_t rd_ser_len = 0;
1168 size_t msg_size = 0;
1169 size_t name_len = 0;
1173 GNUNET_assert (NULL != h);
1174 GNUNET_assert (NULL != pkey);
1175 GNUNET_assert (NULL != name);
1176 GNUNET_assert (NULL != rd);
1178 name_len = strlen(name) + 1;
1186 qe = GNUNET_malloc(sizeof (struct GNUNET_NAMESTORE_QueueEntry));
1189 qe->cont_cls = cont_cls;
1191 GNUNET_CONTAINER_DLL_insert_tail(h->op_head, h->op_tail, qe);
1194 struct GNUNET_CRYPTO_RsaPrivateKeyBinaryEncoded * pkey_enc = GNUNET_CRYPTO_rsa_encode_key (pkey);
1195 GNUNET_assert (pkey_enc != NULL);
1196 key_len = ntohs (pkey_enc->len);
1198 rd_ser_len = GNUNET_NAMESTORE_records_get_size(1, rd);
1199 char rd_ser[rd_ser_len];
1200 GNUNET_NAMESTORE_records_serialize(1, rd, rd_ser_len, rd_ser);
1202 struct RecordCreateMessage * msg;
1203 msg_size = sizeof (struct RecordCreateMessage) + key_len + name_len + rd_ser_len;
1205 /* create msg here */
1206 pe = GNUNET_malloc(sizeof (struct PendingMessage) + msg_size);
1207 pe->size = msg_size;
1208 pe->is_init = GNUNET_NO;
1209 msg = (struct RecordCreateMessage *) &pe[1];
1211 pkey_tmp = (char *) &msg[1];
1212 name_tmp = &pkey_tmp[key_len];
1213 rd_tmp = &name_tmp[name_len];
1215 msg->gns_header.header.type = htons (GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_CREATE);
1216 msg->gns_header.header.size = htons (msg_size);
1217 msg->gns_header.r_id = htonl (rid);
1218 msg->name_len = htons (name_len);
1219 msg->rd_count = htons (1);
1220 msg->rd_len = htons (rd_ser_len);
1221 msg->pkey_len = htons (key_len);
1222 memcpy (pkey_tmp, pkey_enc, key_len);
1223 memcpy (name_tmp, name, name_len);
1224 memcpy (rd_tmp, rd_ser, rd_ser_len);
1225 GNUNET_free (pkey_enc);
1227 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending `%s' message for name `%s' with size %u\n", "NAMESTORE_RECORD_CREATE", name, msg_size);
1229 GNUNET_CONTAINER_DLL_insert_tail (h->pending_head, h->pending_tail, pe);
1236 * Explicitly remove some content from the database. The
1237 * "cont"inuation will be called with status "GNUNET_OK" if content
1238 * was removed, "GNUNET_NO" if no matching entry was found and
1239 * "GNUNET_SYSERR" on all other types of errors.
1240 * This API is used by the authority of a zone.
1242 * @param h handle to the namestore
1243 * @param pkey private key of the zone
1244 * @param name name that is being mapped (at most 255 characters long)
1245 * @param rd record data
1246 * @param cont continuation to call when done
1247 * @param cont_cls closure for cont
1248 * @return handle to abort the request
1250 struct GNUNET_NAMESTORE_QueueEntry *
1251 GNUNET_NAMESTORE_record_remove (struct GNUNET_NAMESTORE_Handle *h,
1252 const struct GNUNET_CRYPTO_RsaPrivateKey *pkey,
1254 const struct GNUNET_NAMESTORE_RecordData *rd,
1255 GNUNET_NAMESTORE_ContinuationWithStatus cont,
1258 struct GNUNET_NAMESTORE_QueueEntry *qe;
1259 struct PendingMessage *pe;
1263 size_t rd_ser_len = 0;
1264 size_t msg_size = 0;
1265 size_t name_len = 0;
1269 GNUNET_assert (NULL != h);
1272 qe = GNUNET_malloc(sizeof (struct GNUNET_NAMESTORE_QueueEntry));
1275 qe->cont_cls = cont_cls;
1277 GNUNET_CONTAINER_DLL_insert_tail(h->op_head, h->op_tail, qe);
1280 struct GNUNET_CRYPTO_RsaPrivateKeyBinaryEncoded * pkey_enc = GNUNET_CRYPTO_rsa_encode_key (pkey);
1281 GNUNET_assert (pkey_enc != NULL);
1282 key_len = ntohs (pkey_enc->len);
1284 rd_ser_len = GNUNET_NAMESTORE_records_get_size(1, rd);
1285 char rd_ser[rd_ser_len];
1286 GNUNET_NAMESTORE_records_serialize(1, rd, rd_ser_len, rd_ser);
1288 name_len = strlen (name) + 1;
1290 struct RecordRemoveMessage * msg;
1291 msg_size = sizeof (struct RecordRemoveMessage) + key_len + name_len + rd_ser_len;
1293 /* create msg here */
1294 pe = GNUNET_malloc(sizeof (struct PendingMessage) + msg_size);
1295 pe->size = msg_size;
1296 pe->is_init = GNUNET_NO;
1297 msg = (struct RecordRemoveMessage *) &pe[1];
1299 pkey_tmp = (char *) &msg[1];
1300 name_tmp = &pkey_tmp[key_len];
1301 rd_tmp = &name_tmp[name_len];
1303 msg->gns_header.header.type = htons (GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_REMOVE);
1304 msg->gns_header.header.size = htons (msg_size);
1305 msg->gns_header.r_id = htonl (rid);
1306 msg->name_len = htons (name_len);
1307 msg->rd_len = htons (rd_ser_len);
1308 msg->rd_count = htons (1);
1309 msg->key_len = htons (key_len);
1310 memcpy (pkey_tmp, pkey_enc, key_len);
1311 memcpy (name_tmp, name, name_len);
1312 memcpy (rd_tmp, rd_ser, rd_ser_len);
1314 GNUNET_free (pkey_enc);
1316 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending `%s' message for name `%s' with size %u\n", "NAMESTORE_RECORD_REMOVE", name, msg_size);
1318 GNUNET_CONTAINER_DLL_insert_tail (h->pending_head, h->pending_tail, pe);
1325 * Get a result for a particular key from the namestore. The processor
1326 * will only be called once.
1328 * @param h handle to the namestore
1329 * @param zone zone to look up a record from
1330 * @param name name to look up
1331 * @param record_type desired record type, 0 for all
1332 * @param proc function to call on the matching records, or with
1333 * NULL (rd_count == 0) if there are no matching records
1334 * @param proc_cls closure for proc
1335 * @return a handle that can be used to
1338 struct GNUNET_NAMESTORE_QueueEntry *
1339 GNUNET_NAMESTORE_lookup_record (struct GNUNET_NAMESTORE_Handle *h,
1340 const GNUNET_HashCode *zone,
1342 uint32_t record_type,
1343 GNUNET_NAMESTORE_RecordProcessor proc, void *proc_cls)
1345 struct GNUNET_NAMESTORE_QueueEntry *qe;
1346 struct PendingMessage *pe;
1347 size_t msg_size = 0;
1348 size_t name_len = 0;
1351 GNUNET_assert (NULL != h);
1352 GNUNET_assert (NULL != zone);
1353 GNUNET_assert (NULL != name);
1355 name_len = strlen (name) + 1;
1356 if ((name_len == 0) || (name_len > 256))
1363 qe = GNUNET_malloc(sizeof (struct GNUNET_NAMESTORE_QueueEntry));
1366 qe->proc_cls = proc_cls;
1368 GNUNET_CONTAINER_DLL_insert_tail(h->op_head, h->op_tail, qe);
1371 msg_size = sizeof (struct LookupNameMessage) + name_len;
1372 pe = GNUNET_malloc(sizeof (struct PendingMessage) + msg_size);
1374 /* create msg here */
1375 struct LookupNameMessage * msg;
1376 pe->size = msg_size;
1377 pe->is_init = GNUNET_NO;
1378 msg = (struct LookupNameMessage *) &pe[1];
1379 msg->gns_header.header.type = htons (GNUNET_MESSAGE_TYPE_NAMESTORE_LOOKUP_NAME);
1380 msg->gns_header.header.size = htons (msg_size);
1381 msg->gns_header.r_id = htonl (rid);
1382 msg->record_type = htonl (record_type);
1384 msg->name_len = htonl (name_len);
1385 memcpy (&msg[1], name, name_len);
1387 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending `%s' message for name `%s'\n", "NAMESTORE_LOOKUP_NAME", name);
1389 /* transmit message */
1390 GNUNET_CONTAINER_DLL_insert_tail (h->pending_head, h->pending_tail, pe);
1398 * Look for an existing PKEY delegation record for a given public key.
1399 * Returns at most one result to the processor.
1401 * @param h handle to the namestore
1402 * @param zone hash of public key of the zone to look up in, never NULL
1403 * @param value_zone hash of the public key of the target zone (value), never NULL
1404 * @param proc function to call on the matching records, or with
1405 * NULL (rd_count == 0) if there are no matching records
1406 * @param proc_cls closure for proc
1407 * @return a handle that can be used to
1410 struct GNUNET_NAMESTORE_QueueEntry *
1411 GNUNET_NAMESTORE_zone_to_name (struct GNUNET_NAMESTORE_Handle *h,
1412 const GNUNET_HashCode *zone,
1413 const GNUNET_HashCode *value_zone,
1414 GNUNET_NAMESTORE_RecordProcessor proc, void *proc_cls)
1416 struct GNUNET_NAMESTORE_QueueEntry *qe;
1417 struct PendingMessage *pe;
1418 size_t msg_size = 0;
1421 GNUNET_assert (NULL != h);
1422 GNUNET_assert (NULL != zone);
1423 GNUNET_assert (NULL != value_zone);
1426 qe = GNUNET_malloc(sizeof (struct GNUNET_NAMESTORE_QueueEntry));
1429 qe->proc_cls = proc_cls;
1431 GNUNET_CONTAINER_DLL_insert_tail(h->op_head, h->op_tail, qe);
1434 msg_size = sizeof (struct ZoneToNameMessage);
1435 pe = GNUNET_malloc(sizeof (struct PendingMessage) + msg_size);
1437 /* create msg here */
1438 struct ZoneToNameMessage * msg;
1439 pe->size = msg_size;
1440 pe->is_init = GNUNET_NO;
1441 msg = (struct ZoneToNameMessage *) &pe[1];
1442 msg->gns_header.header.type = htons (GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_TO_NAME);
1443 msg->gns_header.header.size = htons (msg_size);
1444 msg->gns_header.r_id = htonl (rid);
1446 msg->value_zone = *value_zone;
1448 char * z_tmp = strdup (GNUNET_h2s (zone));
1449 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending `%s' message for zone `%s' in zone `%s'\n",
1450 "NAMESTORE_ZONE_TO_NAME",
1452 GNUNET_h2s (value_zone));
1453 GNUNET_free (z_tmp);
1455 /* transmit message */
1456 GNUNET_CONTAINER_DLL_insert_tail (h->pending_head, h->pending_tail, pe);
1465 * Starts a new zone iteration (used to periodically PUT all of our
1466 * records into our DHT). This MUST lock the GNUNET_NAMESTORE_Handle
1467 * for any other calls than GNUNET_NAMESTORE_zone_iterator_next and
1468 * GNUNET_NAMESTORE_zone_iteration_stop. "proc" will be called once
1469 * immediately, and then again after
1470 * "GNUNET_NAMESTORE_zone_iterator_next" is invoked.
1472 * @param h handle to the namestore
1473 * @param zone zone to access, NULL for all zones
1474 * @param must_have_flags flags that must be set for the record to be returned
1475 * @param must_not_have_flags flags that must NOT be set for the record to be returned
1476 * @param proc function to call on each name from the zone; it
1477 * will be called repeatedly with a value (if available)
1478 * and always once at the end with a name of NULL.
1479 * @param proc_cls closure for proc
1480 * @return an iterator handle to use for iteration
1482 struct GNUNET_NAMESTORE_ZoneIterator *
1483 GNUNET_NAMESTORE_zone_iteration_start (struct GNUNET_NAMESTORE_Handle *h,
1484 const GNUNET_HashCode *zone,
1485 enum GNUNET_NAMESTORE_RecordFlags must_have_flags,
1486 enum GNUNET_NAMESTORE_RecordFlags must_not_have_flags,
1487 GNUNET_NAMESTORE_RecordProcessor proc,
1490 struct GNUNET_NAMESTORE_ZoneIterator *it;
1491 struct PendingMessage *pe;
1492 size_t msg_size = 0;
1495 GNUNET_assert (NULL != h);
1496 GNUNET_assert (NULL != zone);
1499 it = GNUNET_malloc (sizeof (struct GNUNET_NAMESTORE_ZoneIterator));
1502 it->proc_cls = proc;
1505 GNUNET_CONTAINER_DLL_insert_tail(h->z_head, h->z_tail, it);
1508 msg_size = sizeof (struct ZoneIterationStartMessage);
1509 pe = GNUNET_malloc(sizeof (struct PendingMessage) + msg_size);
1511 /* create msg here */
1512 struct ZoneIterationStartMessage * msg;
1513 pe->size = msg_size;
1514 pe->is_init = GNUNET_NO;
1515 msg = (struct ZoneIterationStartMessage *) &pe[1];
1516 msg->gns_header.header.type = htons (GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_ITERATION_START);
1517 msg->gns_header.header.size = htons (msg_size);
1518 msg->gns_header.r_id = htonl (rid);
1520 msg->must_have_flags = ntohs (must_have_flags);
1521 msg->must_not_have_flags = ntohs (must_not_have_flags);
1523 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending `%s' message for zone `%s'\n", "ZONE_ITERATION_START", GNUNET_h2s(zone));
1525 /* transmit message */
1526 GNUNET_CONTAINER_DLL_insert_tail (h->pending_head, h->pending_tail, pe);
1534 * Calls the record processor specified in GNUNET_NAMESTORE_zone_iteration_start
1535 * for the next record.
1537 * @param it the iterator
1540 GNUNET_NAMESTORE_zone_iterator_next (struct GNUNET_NAMESTORE_ZoneIterator *it)
1542 struct GNUNET_NAMESTORE_Handle *h;
1543 struct PendingMessage *pe;
1544 size_t msg_size = 0;
1546 GNUNET_assert (NULL != it);
1550 msg_size = sizeof (struct ZoneIterationNextMessage);
1551 pe = GNUNET_malloc(sizeof (struct PendingMessage) + msg_size);
1553 /* create msg here */
1554 struct ZoneIterationNextMessage * msg;
1555 pe->size = msg_size;
1556 pe->is_init = GNUNET_NO;
1557 msg = (struct ZoneIterationNextMessage *) &pe[1];
1558 msg->gns_header.header.type = htons (GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_ITERATION_NEXT);
1559 msg->gns_header.header.size = htons (msg_size);
1560 msg->gns_header.r_id = htonl (it->op_id);
1562 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending `%s' message for name `%s'\n", "ZONE_ITERATION_NEXT", GNUNET_h2s(&it->zone));
1564 /* transmit message */
1565 GNUNET_CONTAINER_DLL_insert_tail (h->pending_head, h->pending_tail, pe);
1571 * Stops iteration and releases the namestore handle for further calls.
1573 * @param it the iterator
1576 GNUNET_NAMESTORE_zone_iteration_stop (struct GNUNET_NAMESTORE_ZoneIterator *it)
1578 GNUNET_assert (NULL != it);
1579 struct PendingMessage *pe;
1580 size_t msg_size = 0;
1581 struct GNUNET_NAMESTORE_Handle *h = it->h;
1584 msg_size = sizeof (struct ZoneIterationStopMessage);
1585 pe = GNUNET_malloc(sizeof (struct PendingMessage) + msg_size);
1587 /* create msg here */
1588 struct ZoneIterationStopMessage * msg;
1589 pe->size = msg_size;
1590 pe->is_init = GNUNET_NO;
1591 msg = (struct ZoneIterationStopMessage *) &pe[1];
1592 msg->gns_header.header.type = htons (GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_ITERATION_STOP);
1593 msg->gns_header.header.size = htons (msg_size);
1594 msg->gns_header.r_id = htonl (it->op_id);
1596 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending `%s' message for name `%s'\n", "ZONE_ITERATION_STOP", GNUNET_h2s(&it->zone));
1598 /* transmit message */
1599 GNUNET_CONTAINER_DLL_insert_tail (h->pending_head, h->pending_tail, pe);
1605 * Cancel a namestore operation. The final callback from the
1606 * operation must not have been done yet.
1608 * @param qe operation to cancel
1611 GNUNET_NAMESTORE_cancel (struct GNUNET_NAMESTORE_QueueEntry *qe)
1613 struct GNUNET_NAMESTORE_Handle *h = qe->nsh;
1615 GNUNET_assert (qe != NULL);
1617 GNUNET_CONTAINER_DLL_remove(h->op_head, h->op_tail, qe);
1622 /* end of namestore_api.c */