2 This file is part of GNUnet.
3 (C) 2009 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/gnunet-service-namestore.c
23 * @brief namestore for the GNUnet naming system
24 * @author Matthias Wachs
27 #include "gnunet_getopt_lib.h"
28 #include "gnunet_service_lib.h"
29 #include "gnunet_namestore_service.h"
30 #include "gnunet_namestore_plugin.h"
31 #include "gnunet_signatures.h"
32 #include "namestore.h"
37 * A namestore operation.
39 struct GNUNET_NAMESTORE_ZoneIteration
41 struct GNUNET_NAMESTORE_ZoneIteration *next;
42 struct GNUNET_NAMESTORE_ZoneIteration *prev;
44 struct GNUNET_NAMESTORE_Client * client;
61 struct GNUNET_NAMESTORE_Client
63 struct GNUNET_NAMESTORE_Client *next;
64 struct GNUNET_NAMESTORE_Client *prev;
66 struct GNUNET_SERVER_Client * client;
68 struct GNUNET_NAMESTORE_ZoneIteration *op_head;
69 struct GNUNET_NAMESTORE_ZoneIteration *op_tail;
75 * Configuration handle.
77 const struct GNUNET_CONFIGURATION_Handle *GSN_cfg;
79 static struct GNUNET_NAMESTORE_PluginFunctions *GSN_database;
82 * Our notification context.
84 static struct GNUNET_SERVER_NotificationContext *snc;
86 static char *db_lib_name;
88 static struct GNUNET_NAMESTORE_Client *client_head;
89 static struct GNUNET_NAMESTORE_Client *client_tail;
93 * Task run during shutdown.
99 cleanup_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc)
101 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stopping namestore service\n");
103 struct GNUNET_NAMESTORE_ZoneIteration * no;
104 struct GNUNET_NAMESTORE_ZoneIteration * tmp;
105 struct GNUNET_NAMESTORE_Client * nc;
106 struct GNUNET_NAMESTORE_Client * next;
108 GNUNET_SERVER_notification_context_destroy (snc);
111 for (nc = client_head; nc != NULL; nc = next)
114 for (no = nc->op_head; no != NULL; no = tmp)
117 GNUNET_CONTAINER_DLL_remove (nc->op_head, nc->op_tail, no);
121 GNUNET_SERVER_client_drop(nc->client);
122 GNUNET_CONTAINER_DLL_remove (client_head, client_tail, nc);
126 GNUNET_break (NULL == GNUNET_PLUGIN_unload (db_lib_name, GSN_database));
127 GNUNET_free (db_lib_name);
130 static struct GNUNET_NAMESTORE_Client *
131 client_lookup (struct GNUNET_SERVER_Client *client)
133 struct GNUNET_NAMESTORE_Client * nc;
135 GNUNET_assert (NULL != client);
137 for (nc = client_head; nc != NULL; nc = nc->next)
139 if (client == nc->client)
146 * Called whenever a client is disconnected. Frees our
147 * resources associated with that client.
150 * @param client identification of the client
153 client_disconnect_notification (void *cls, struct GNUNET_SERVER_Client *client)
155 struct GNUNET_NAMESTORE_ZoneIteration * no;
156 struct GNUNET_NAMESTORE_Client * nc;
160 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Client %p disconnected \n", client);
162 nc = client_lookup (client);
164 if ((NULL == client) || (NULL == nc))
167 for (no = nc->op_head; no != NULL; no = no->next)
169 GNUNET_CONTAINER_DLL_remove (nc->op_head, nc->op_tail, no);
174 GNUNET_SERVER_client_drop(nc->client);
175 GNUNET_CONTAINER_DLL_remove (client_head, client_tail, nc);
181 static void handle_start (void *cls,
182 struct GNUNET_SERVER_Client * client,
183 const struct GNUNET_MessageHeader * message)
185 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Client %p connected\n", client);
187 struct GNUNET_NAMESTORE_Client * nc = GNUNET_malloc (sizeof (struct GNUNET_NAMESTORE_Client));
189 GNUNET_SERVER_notification_context_add (snc, client);
190 GNUNET_CONTAINER_DLL_insert(client_head, client_tail, nc);
191 GNUNET_SERVER_client_keep (client);
192 GNUNET_SERVER_receive_done (client, GNUNET_OK);
195 struct LookupNameContext
197 struct GNUNET_NAMESTORE_Client *nc;
199 uint32_t record_type;
200 GNUNET_HashCode *zone;
204 void drop_iterator (void *cls,
205 const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key,
206 struct GNUNET_TIME_Absolute expire,
209 const struct GNUNET_NAMESTORE_RecordData *rd,
210 const struct GNUNET_CRYPTO_RsaSignature *signature)
212 GNUNET_HashCode zone_hash;
214 if (NULL != zone_key)
216 GNUNET_CRYPTO_hash(zone_key, sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), &zone_hash);
217 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Deleting zone `%s'\n", GNUNET_h2s (&zone_hash));
218 GSN_database->delete_zone (GSN_database->cls, &zone_hash);
222 (*stop) = GNUNET_YES;
228 handle_lookup_name_it (void *cls,
229 const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key,
230 struct GNUNET_TIME_Absolute expire,
232 unsigned int rd_count,
233 const struct GNUNET_NAMESTORE_RecordData *rd,
234 const struct GNUNET_CRYPTO_RsaSignature *signature)
237 struct LookupNameContext *lnc = cls;
238 struct LookupNameResponseMessage *lnr_msg;
239 struct GNUNET_NAMESTORE_RecordData *rd_selected = NULL;
246 int copied_elements = 0;
247 int contains_signature = 0;
251 name_len = strlen(name) + 1;
253 /* count records to copy */
256 if (lnc->record_type != 0)
258 /* special record type needed */
259 for (c = 0; c < rd_count; c ++)
260 if (rd[c].record_type == lnc->record_type)
261 copied_elements++; /* found matching record */
262 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Found %u records with type %u for name `%s' in zone `%s'\n",
263 copied_elements, lnc->record_type, lnc->name, GNUNET_h2s(lnc->zone));
264 rd_selected = GNUNET_malloc (copied_elements * sizeof (struct GNUNET_NAMESTORE_RecordData));
266 for (c = 0; c < rd_count; c ++)
268 if (rd[c].record_type == lnc->record_type)
270 /* found matching record */
271 memcpy (&rd_selected[copied_elements], &rd[c], sizeof (struct GNUNET_NAMESTORE_RecordData));
278 copied_elements = rd_count;
279 rd_selected = (struct GNUNET_NAMESTORE_RecordData *) rd;
287 expire = GNUNET_TIME_UNIT_ZERO_ABS;
290 rd_ser_len = GNUNET_NAMESTORE_records_get_size(copied_elements, rd_selected);
291 char rd_ser[rd_ser_len];
292 GNUNET_NAMESTORE_records_serialize(copied_elements, rd_selected, rd_ser_len, rd_ser);
294 if (rd_selected != rd)
295 GNUNET_free (rd_selected);
297 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Found %u records for name `%s' in zone `%s'\n",
298 copied_elements, lnc->name, GNUNET_h2s(lnc->zone));
300 if ((copied_elements == rd_count) && (NULL != signature))
301 contains_signature = GNUNET_YES;
303 contains_signature = GNUNET_NO;
305 r_size = sizeof (struct LookupNameResponseMessage) +
306 sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded) +
310 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending `%s' message\n", "NAMESTORE_LOOKUP_NAME_RESPONSE");
311 lnr_msg = GNUNET_malloc (r_size);
312 lnr_msg->gns_header.header.type = ntohs (GNUNET_MESSAGE_TYPE_NAMESTORE_LOOKUP_NAME_RESPONSE);
313 lnr_msg->gns_header.header.size = ntohs (r_size);
314 lnr_msg->gns_header.r_id = htonl (lnc->request_id);
315 lnr_msg->rd_count = htons (copied_elements);
316 lnr_msg->rd_len = htons (rd_ser_len);
317 lnr_msg->name_len = htons (name_len);
318 lnr_msg->contains_sig = htons (contains_signature);
319 lnr_msg->expire = GNUNET_TIME_absolute_hton(expire);
321 if (zone_key != NULL)
322 lnr_msg->public_key = (*zone_key);
324 memset(&lnr_msg->public_key, '\0', sizeof (lnr_msg->public_key));
325 if (GNUNET_YES == contains_signature)
326 lnr_msg->signature = *signature;
328 memset (&lnr_msg->signature, '\0', sizeof (lnr_msg->signature));
330 name_tmp = (char *) &lnr_msg[1];
331 rd_tmp = &name_tmp[name_len];
333 memcpy (name_tmp, name, name_len);
334 memcpy (rd_tmp, rd_ser, rd_ser_len);
336 GNUNET_SERVER_notification_context_unicast (snc, lnc->nc->client, (const struct GNUNET_MessageHeader *) lnr_msg, GNUNET_NO);
338 GNUNET_free (lnr_msg);
341 static void handle_lookup_name (void *cls,
342 struct GNUNET_SERVER_Client * client,
343 const struct GNUNET_MessageHeader * message)
345 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received `%s' message\n", "NAMESTORE_LOOKUP_NAME");
346 struct LookupNameContext lnc;
347 struct GNUNET_NAMESTORE_Client *nc;
353 if (ntohs (message->size) < sizeof (struct LookupNameMessage))
356 GNUNET_SERVER_receive_done (client, GNUNET_OK);
360 nc = client_lookup(client);
364 GNUNET_SERVER_receive_done (client, GNUNET_OK);
368 struct LookupNameMessage * ln_msg = (struct LookupNameMessage *) message;
369 rid = ntohl (ln_msg->gns_header.r_id);
370 name_len = ntohl (ln_msg->name_len);
371 type = ntohl (ln_msg->record_type);
373 if ((name_len == 0) || (name_len > 256))
376 GNUNET_SERVER_receive_done (client, GNUNET_OK);
380 name = (char *) &ln_msg[1];
381 if (name[name_len -1] != '\0')
384 GNUNET_SERVER_receive_done (client, GNUNET_OK);
389 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Looking up all records for name `%s' in zone `%s'\n", name, GNUNET_h2s(&ln_msg->zone));
391 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Looking up records with type %u for name `%s' in zone `%s'\n", type, name, GNUNET_h2s(&ln_msg->zone));
393 /* do the actual lookup */
394 lnc.request_id = rid;
396 lnc.record_type = type;
398 lnc.zone = &ln_msg->zone;
399 GSN_database->iterate_records(GSN_database->cls, &ln_msg->zone, name, 0, &handle_lookup_name_it, &lnc);
401 GNUNET_SERVER_receive_done (client, GNUNET_OK);
404 static void handle_record_put (void *cls,
405 struct GNUNET_SERVER_Client * client,
406 const struct GNUNET_MessageHeader * message)
408 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received `%s' message\n", "NAMESTORE_RECORD_PUT");
409 struct GNUNET_NAMESTORE_Client *nc;
410 struct GNUNET_TIME_Absolute expire;
411 struct GNUNET_CRYPTO_RsaSignature *signature;
412 struct RecordPutResponseMessage rpr_msg;
421 int res = GNUNET_SYSERR;
423 if (ntohs (message->size) < sizeof (struct RecordPutMessage))
426 GNUNET_SERVER_receive_done (client, GNUNET_OK);
430 nc = client_lookup (client);
434 GNUNET_SERVER_receive_done (client, GNUNET_OK);
438 struct RecordPutMessage * rp_msg = (struct RecordPutMessage *) message;
440 rid = ntohl (rp_msg->gns_header.r_id);
441 msg_size = ntohs (rp_msg->gns_header.header.size);
442 name_len = ntohs (rp_msg->name_len);
443 rd_count = ntohs (rp_msg->rd_count);
444 rd_ser_len = ntohs(rp_msg->rd_len);
446 if (msg_size > GNUNET_SERVER_MAX_MESSAGE_SIZE)
449 GNUNET_SERVER_receive_done (client, GNUNET_OK);
453 if ((rd_count < 1) || (rd_ser_len < 1) || (name_len >=256) || (name_len == 0))
456 GNUNET_SERVER_receive_done (client, GNUNET_OK);
460 msg_size_exp = sizeof (struct RecordPutMessage) + name_len + rd_ser_len;
461 if (msg_size != msg_size_exp)
463 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Expected message %u size but message size is %u \n", msg_size_exp, msg_size);
465 GNUNET_SERVER_receive_done (client, GNUNET_OK);
468 if ((name_len == 0) || (name_len > 256))
471 GNUNET_SERVER_receive_done (client, GNUNET_OK);
475 name = (char *) &rp_msg[1];
477 if (name[name_len -1] != '\0')
480 GNUNET_SERVER_receive_done (client, GNUNET_OK);
484 expire = GNUNET_TIME_absolute_ntoh(rp_msg->expire);
485 signature = (struct GNUNET_CRYPTO_RsaSignature *) &rp_msg->signature;
487 rd_ser = &name[name_len];
488 struct GNUNET_NAMESTORE_RecordData rd[rd_count];
489 res = GNUNET_NAMESTORE_records_deserialize(rd_ser_len, rd_ser, rd_count, rd);
490 if (res != GNUNET_OK)
496 GNUNET_HashCode zone_hash;
497 GNUNET_CRYPTO_hash (&rp_msg->public_key, sizeof (rp_msg->public_key), &zone_hash);
499 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Putting %u record for name `%s' in zone `%s'\n", rd_count, name, GNUNET_h2s(&zone_hash));
501 /* Database operation */
502 res = GSN_database->put_records(GSN_database->cls,
509 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Putting record for name `%s': %s\n",
510 name, (res == GNUNET_OK) ? "OK" : "FAIL");
514 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending `%s' message\n", "RECORD_PUT_RESPONSE");
515 rpr_msg.gns_header.header.type = htons (GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_PUT_RESPONSE);
516 rpr_msg.gns_header.header.size = htons (sizeof (struct RecordPutResponseMessage));
517 rpr_msg.gns_header.r_id = htonl (rid);
518 rpr_msg.op_result = htonl (res);
519 GNUNET_SERVER_notification_context_unicast (snc, nc->client, (const struct GNUNET_MessageHeader *) &rpr_msg, GNUNET_NO);
521 GNUNET_SERVER_receive_done (client, GNUNET_OK);
524 struct CreateRecordContext
526 struct GNUNET_NAMESTORE_RecordData *rd;
527 struct GNUNET_CRYPTO_RsaPrivateKey *pkey;
528 struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *pubkey;
529 struct GNUNET_TIME_Absolute expire;
536 handle_create_record_it (void *cls,
537 const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *pubkey,
538 struct GNUNET_TIME_Absolute expire,
540 unsigned int rd_count,
541 const struct GNUNET_NAMESTORE_RecordData *rd,
542 const struct GNUNET_CRYPTO_RsaSignature *signature)
544 struct CreateRecordContext * crc = cls;
545 struct GNUNET_CRYPTO_RsaSignature *signature_new = NULL;
546 struct GNUNET_NAMESTORE_RecordData *rd_new = NULL;
547 struct GNUNET_TIME_Absolute block_expiration;
549 int exist = GNUNET_SYSERR;
550 int update = GNUNET_NO;
552 int rd_count_new = 0;
554 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Found %u existing records for `%s'\n", rd_count, crc->name);
556 for (c = 0; c < rd_count; c++)
559 if ((crc->rd->record_type == rd[c].record_type) &&
560 (crc->rd->data_size == rd[c].data_size) &&
561 (0 == memcmp (crc->rd->data, rd[c].data, rd[c].data_size)))
563 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Found existing records for `%s' to update expiration date!\n", crc->name);
565 if (crc->rd->expiration.abs_value != rd[c].expiration.abs_value)
571 if (exist == GNUNET_SYSERR)
572 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "NO existing records for `%s' to update!\n", crc->name);
574 if (exist == GNUNET_SYSERR)
576 rd_new = GNUNET_malloc ((rd_count+1) * sizeof (struct GNUNET_NAMESTORE_RecordData));
577 memcpy (rd_new, rd, rd_count * sizeof (struct GNUNET_NAMESTORE_RecordData));
578 rd_count_new = rd_count + 1;
579 rd_new[rd_count] = *(crc->rd);
580 signature_new = GNUNET_NAMESTORE_create_signature (crc->pkey, crc->name, rd_new, rd_count+1);
582 if (NULL == signature_new)
589 else if (update == GNUNET_NO)
591 /* Exact same record already exists */
592 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "No update for %s' record required!\n", crc->name);
596 else if (update == GNUNET_YES)
599 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Updating existing records for `%s'!\n", crc->name);
600 rd_new = GNUNET_malloc ((rd_count) * sizeof (struct GNUNET_NAMESTORE_RecordData));
601 memcpy (rd_new, rd, rd_count * sizeof (struct GNUNET_NAMESTORE_RecordData));
602 rd_count_new = rd_count;
603 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Updating expiration from %llu to %llu!\n", rd_new[exist].expiration.abs_value, crc->rd->expiration.abs_value);
604 rd_new[exist].expiration = crc->rd->expiration;
605 signature_new = GNUNET_NAMESTORE_create_signature (crc->pkey, crc->name, rd_new, rd_count_new);
606 if (NULL == signature_new)
614 block_expiration = GNUNET_TIME_absolute_max(crc->expire, expire);
615 if (block_expiration.abs_value != expire.abs_value)
616 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Updated block expiration time\n");
619 /* Database operation */
620 GNUNET_assert ((rd_new != NULL) && (rd_count_new > 0));
621 res = GSN_database->put_records(GSN_database->cls,
622 (const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *) crc->pubkey,
625 rd_count_new, rd_new,
627 GNUNET_break (GNUNET_OK == res);
628 if (res == GNUNET_OK)
629 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Successfully put record for `%s' in database \n", crc->name);
631 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Failed to put record for `%s' in database \n", crc->name);
635 GNUNET_free_non_null (rd_new);
636 GNUNET_free_non_null (signature_new);
640 /* failed to create the record */
641 crc->res = GNUNET_SYSERR;
644 /* database operations OK */
645 if (GNUNET_YES == update)
646 /* we updated an existing record */
647 crc->res = GNUNET_NO;
649 /* we created a new record */
650 crc->res = GNUNET_YES;
653 /* identical entry existed, so we did nothing */
654 crc->res = GNUNET_NO;
660 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Update result for name `%s' %u\n", crc->name, res);
664 static void handle_record_create (void *cls,
665 struct GNUNET_SERVER_Client * client,
666 const struct GNUNET_MessageHeader * message)
668 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received `%s' message\n", "NAMESTORE_RECORD_CREATE");
669 struct GNUNET_NAMESTORE_Client *nc;
670 struct CreateRecordContext crc;
671 struct GNUNET_CRYPTO_RsaPrivateKey *pkey;
672 struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded pub;
673 struct RecordCreateResponseMessage rcr_msg;
674 GNUNET_HashCode pubkey_hash;
686 int res = GNUNET_SYSERR;
688 if (ntohs (message->size) < sizeof (struct RecordCreateMessage))
691 GNUNET_SERVER_receive_done (client, GNUNET_OK);
695 nc = client_lookup(client);
699 GNUNET_SERVER_receive_done (client, GNUNET_OK);
703 struct RecordCreateMessage * rp_msg = (struct RecordCreateMessage *) message;
704 rid = ntohl (rp_msg->gns_header.r_id);
705 name_len = ntohs (rp_msg->name_len);
706 msg_size = ntohs (message->size);
707 rd_count = ntohs (rp_msg->rd_count);
708 rd_ser_len = ntohs (rp_msg->rd_len);
709 key_len = ntohs (rp_msg->pkey_len);
710 msg_size_exp = sizeof (struct RecordCreateMessage) + key_len + name_len + rd_ser_len;
712 if (msg_size != msg_size_exp)
714 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Expected message %u size but message size is %u \n", msg_size_exp, msg_size);
716 GNUNET_SERVER_receive_done (client, GNUNET_OK);
720 if ((name_len == 0) || (name_len > 256))
723 GNUNET_SERVER_receive_done (client, GNUNET_OK);
727 pkey_tmp = (char *) &rp_msg[1];
728 name_tmp = &pkey_tmp[key_len];
729 rd_ser = &name_tmp[name_len];
731 if (name_tmp[name_len -1] != '\0')
734 GNUNET_SERVER_receive_done (client, GNUNET_OK);
738 struct GNUNET_NAMESTORE_RecordData rd[rd_count];
740 res = GNUNET_NAMESTORE_records_deserialize(rd_ser_len, rd_ser, rd_count, rd);
741 if ((res != GNUNET_OK) || (rd_count != 1))
747 /* Extracting and converting private key */
748 pkey = GNUNET_CRYPTO_rsa_decode_key((char *) pkey_tmp, key_len);
749 GNUNET_assert (pkey != NULL);
750 GNUNET_CRYPTO_rsa_key_get_public(pkey, &pub);
751 GNUNET_CRYPTO_hash (&pub, sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), &pubkey_hash);
753 crc.expire = GNUNET_TIME_absolute_ntoh(rp_msg->expire);
754 crc.res = GNUNET_SYSERR;
760 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Creating record for name `%s' in zone `%s'\n", name_tmp, GNUNET_h2s(&pubkey_hash));
762 /* Get existing records for name */
763 res = GSN_database->iterate_records(GSN_database->cls, &pubkey_hash, name_tmp, 0, &handle_create_record_it, &crc);
764 if (res != GNUNET_SYSERR)
766 GNUNET_CRYPTO_rsa_key_free(pkey);
770 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending `%s' message\n", "RECORD_CREATE_RESPONSE");
771 rcr_msg.gns_header.header.type = htons (GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_CREATE_RESPONSE);
772 rcr_msg.gns_header.header.size = htons (sizeof (struct RecordCreateResponseMessage));
773 rcr_msg.gns_header.r_id = htonl (rid);
774 if ((GNUNET_OK == res) && (crc.res == GNUNET_YES))
775 rcr_msg.op_result = htonl (GNUNET_YES);
776 else if ((GNUNET_OK == res) && (crc.res == GNUNET_NO))
777 rcr_msg.op_result = htonl (GNUNET_NO);
779 rcr_msg.op_result = htonl (GNUNET_SYSERR);
780 GNUNET_SERVER_notification_context_unicast (snc, nc->client, (const struct GNUNET_MessageHeader *) &rcr_msg, GNUNET_NO);
782 GNUNET_SERVER_receive_done (client, GNUNET_OK);
786 struct RemoveRecordContext
788 struct GNUNET_NAMESTORE_RecordData *rd;
789 struct GNUNET_CRYPTO_RsaPrivateKey *pkey;
794 handle_record_remove_it (void *cls,
795 const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key,
796 struct GNUNET_TIME_Absolute expire,
798 unsigned int rd_count,
799 const struct GNUNET_NAMESTORE_RecordData *rd,
800 const struct GNUNET_CRYPTO_RsaSignature *signature)
802 struct RemoveRecordContext *rrc = cls;
803 unsigned int rd_count_new = rd_count -1;
804 struct GNUNET_NAMESTORE_RecordData rd_new[rd_count_new];
807 int found = GNUNET_NO;
809 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Name `%s 'currently has %u records\n", name, rd_count);
813 /* Could not find record to remove */
818 /* Find record to remove */
820 for (c = 0; c < rd_count; c++)
822 if ((rd[c].expiration.abs_value == rrc->rd->expiration.abs_value) &&
823 (rd[c].flags == rrc->rd->flags) &&
824 (rd[c].record_type == rrc->rd->record_type) &&
825 (rd[c].data_size == rrc->rd->data_size) &&
826 (0 == memcmp (rd[c].data, rrc->rd->data, rrc->rd->data_size)))
828 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Found record to remove!\n", rd_count);
838 if ((c2 != rd_count_new) || (found == GNUNET_NO))
840 /* Could not find record to remove */
844 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Name `%s' now has %u records\n", name, rd_count_new);
846 /* Create new signature */
847 struct GNUNET_CRYPTO_RsaSignature * new_signature;
848 new_signature = GNUNET_NAMESTORE_create_signature (rrc->pkey, name, rd_new, rd_count_new);
850 if (new_signature == NULL)
852 /* Signature failed */
858 res = GSN_database->put_records(GSN_database->cls,
862 rd_count_new, rd_new,
864 GNUNET_free (new_signature);
866 if (GNUNET_OK != res)
868 /* Could put records into database */
876 static void handle_record_remove (void *cls,
877 struct GNUNET_SERVER_Client * client,
878 const struct GNUNET_MessageHeader * message)
880 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received `%s' message\n", "NAMESTORE_RECORD_REMOVE");
881 struct GNUNET_NAMESTORE_Client *nc;
882 struct RecordRemoveResponseMessage rrr_msg;
883 struct GNUNET_CRYPTO_RsaPrivateKey *pkey;
884 struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded pub;
885 GNUNET_HashCode pubkey_hash;
886 char * pkey_tmp = NULL;
887 char * name_tmp = NULL;
888 char * rd_ser = NULL;
891 size_t rd_ser_len = 0;
893 size_t msg_size_exp = 0;
897 int res = GNUNET_SYSERR;
899 if (ntohs (message->size) < sizeof (struct RecordRemoveMessage))
902 GNUNET_SERVER_receive_done (client, GNUNET_OK);
906 nc = client_lookup(client);
910 GNUNET_SERVER_receive_done (client, GNUNET_OK);
914 struct RecordRemoveMessage * rr_msg = (struct RecordRemoveMessage *) message;
915 rid = ntohl (rr_msg->gns_header.r_id);
916 name_len = ntohs (rr_msg->name_len);
917 rd_ser_len = ntohs (rr_msg->rd_len);
918 rd_count = ntohs (rr_msg->rd_count);
919 key_len = ntohs (rr_msg->pkey_len);
920 msg_size = ntohs (message->size);
922 if (msg_size > GNUNET_SERVER_MAX_MESSAGE_SIZE)
925 GNUNET_SERVER_receive_done (client, GNUNET_OK);
929 if ((rd_count != 1) || (rd_ser_len < 1) || (name_len >=256) || (name_len == 0))
932 GNUNET_SERVER_receive_done (client, GNUNET_OK);
936 msg_size_exp = sizeof (struct RecordRemoveMessage) + key_len + name_len + rd_ser_len;
937 if (msg_size != msg_size_exp)
939 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Expected message %u size but message size is %u \n", msg_size_exp, msg_size);
941 GNUNET_SERVER_receive_done (client, GNUNET_OK);
945 if ((rd_count != 1) || (rd_ser_len < 1) || (name_len >=256) || (name_len == 0))
948 GNUNET_SERVER_receive_done (client, GNUNET_OK);
952 pkey_tmp = (char *) &rr_msg[1];
953 name_tmp = &pkey_tmp[key_len];
954 rd_ser = &name_tmp[name_len];
957 if ((name_len == 0) || (name_len > 256))
960 GNUNET_SERVER_receive_done (client, GNUNET_OK);
964 if (name_tmp[name_len -1] != '\0')
967 GNUNET_SERVER_receive_done (client, GNUNET_OK);
971 /* Extracting and converting private key */
972 pkey = GNUNET_CRYPTO_rsa_decode_key((char *) pkey_tmp, key_len);
973 GNUNET_assert (pkey != NULL);
974 GNUNET_CRYPTO_rsa_key_get_public(pkey, &pub);
975 GNUNET_CRYPTO_hash (&pub, sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded), &pubkey_hash);
977 struct GNUNET_NAMESTORE_RecordData rd[rd_count];
978 res = GNUNET_NAMESTORE_records_deserialize(rd_ser_len, rd_ser, rd_count, rd);
979 if ((res != GNUNET_OK) || (rd_count != 1))
985 struct RemoveRecordContext rrc;
989 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Removing record for name `%s' in zone `%s'\n", name_tmp, GNUNET_h2s(&pubkey_hash));
991 /* Database operation */
992 res = GSN_database->iterate_records (GSN_database->cls,
996 handle_record_remove_it, &rrc);
998 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Removing record for name `%s': %s\n",
999 name_tmp, (rrc.op_res == 0) ? "OK" : "FAIL");
1004 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending `%s' message\n", "RECORD_REMOVE_RESPONSE");
1005 rrr_msg.gns_header.header.type = htons (GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_REMOVE_RESPONSE);
1006 rrr_msg.gns_header.header.size = htons (sizeof (struct RecordRemoveResponseMessage));
1007 rrr_msg.gns_header.r_id = htonl (rid);
1008 rrr_msg.op_result = htonl (res);
1009 GNUNET_SERVER_notification_context_unicast (snc, nc->client, (const struct GNUNET_MessageHeader *) &rrr_msg, GNUNET_NO);
1011 GNUNET_CRYPTO_rsa_key_free (pkey);
1013 GNUNET_SERVER_receive_done (client, GNUNET_OK);
1017 struct ZoneToNameCtx
1019 struct GNUNET_NAMESTORE_Client *nc;
1024 handle_zone_to_name_it (void *cls,
1025 const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key,
1026 struct GNUNET_TIME_Absolute expire,
1028 unsigned int rd_count,
1029 const struct GNUNET_NAMESTORE_RecordData *rd,
1030 const struct GNUNET_CRYPTO_RsaSignature *signature)
1032 struct ZoneToNameCtx * ztn_ctx = cls;
1033 struct ZoneToNameResponseMessage *ztnr_msg;
1034 int16_t res = GNUNET_SYSERR;
1035 uint16_t name_len = 0;
1036 uint16_t rd_ser_len = 0 ;
1037 int32_t contains_sig = 0;
1038 size_t msg_size = 0;
1040 char *rd_ser = NULL;
1045 if ((zone_key != NULL) && (name != NULL))
1048 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Found results: name is `%s', has %u records\n", name, rd_count);
1050 name_len = strlen (name);
1054 /* no result found */
1055 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Found no results\n");
1062 rd_ser_len = GNUNET_NAMESTORE_records_get_size (rd_count, rd);
1063 rd_ser = GNUNET_malloc (rd_ser_len);
1064 GNUNET_NAMESTORE_records_serialize(rd_count, rd, rd_ser_len, rd_ser);
1069 if (signature != NULL)
1070 contains_sig = GNUNET_YES;
1072 contains_sig = GNUNET_NO;
1076 msg_size = sizeof (struct ZoneToNameResponseMessage) + name_len + rd_ser_len + contains_sig * sizeof (struct GNUNET_CRYPTO_RsaSignature);
1077 ztnr_msg = GNUNET_malloc (msg_size);
1079 name_tmp = (char *) &ztnr_msg[1];
1080 rd_tmp = &name_tmp[name_len];
1081 sig_tmp = &rd_tmp[rd_ser_len];
1083 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending `%s' message\n", "ZONE_TO_NAME_RESPONSE");
1084 ztnr_msg->gns_header.header.type = htons (GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_TO_NAME_RESPONSE);
1085 ztnr_msg->gns_header.header.size = htons (msg_size);
1086 ztnr_msg->gns_header.r_id = htonl (ztn_ctx->rid);
1087 ztnr_msg->res = htons (res);
1088 ztnr_msg->rd_len = htons (rd_ser_len);
1089 ztnr_msg->rd_count = htons (rd_count);
1090 ztnr_msg->name_len = htons (name_len);
1091 ztnr_msg->expire = GNUNET_TIME_absolute_hton(expire);
1092 if (zone_key != NULL)
1093 ztnr_msg->zone_key = *zone_key;
1095 memset (&ztnr_msg->zone_key, '\0', sizeof (struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded));
1097 memcpy (name_tmp, name, name_len);
1099 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Name is `%s', has %u records, rd ser len %u msg_size %u\n", name, rd_count, rd_ser_len, msg_size);
1100 memcpy (rd_tmp, rd_ser, rd_ser_len);
1101 memcpy (sig_tmp, signature, contains_sig * sizeof (struct GNUNET_CRYPTO_RsaSignature));
1103 GNUNET_SERVER_notification_context_unicast (snc, ztn_ctx->nc->client, (const struct GNUNET_MessageHeader *) ztnr_msg, GNUNET_NO);
1104 GNUNET_free (ztnr_msg);
1105 GNUNET_free_non_null (rd_ser);
1109 static void handle_zone_to_name (void *cls,
1110 struct GNUNET_SERVER_Client * client,
1111 const struct GNUNET_MessageHeader * message)
1113 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received `%s' message\n", "ZONE_TO_NAME");
1114 struct GNUNET_NAMESTORE_Client *nc;
1115 struct ZoneToNameCtx ztn_ctx;
1116 size_t msg_size = 0;
1119 if (ntohs (message->size) != sizeof (struct ZoneToNameMessage))
1121 GNUNET_break_op (0);
1122 GNUNET_SERVER_receive_done (client, GNUNET_OK);
1126 nc = client_lookup(client);
1129 GNUNET_break_op (0);
1130 GNUNET_SERVER_receive_done (client, GNUNET_OK);
1134 struct ZoneToNameMessage *ztn_msg = (struct ZoneToNameMessage *) message;
1136 if (msg_size > GNUNET_SERVER_MAX_MESSAGE_SIZE)
1138 GNUNET_break_op (0);
1139 GNUNET_SERVER_receive_done (client, GNUNET_OK);
1143 rid = ntohl (ztn_msg->gns_header.r_id);
1148 char * z_tmp = strdup (GNUNET_h2s (&ztn_msg->zone));
1149 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Looking up name for zone `%s' in zone `%s'\n",
1151 GNUNET_h2s (&ztn_msg->value_zone));
1152 GNUNET_free (z_tmp);
1154 GSN_database->zone_to_name (GSN_database->cls, &ztn_msg->zone, &ztn_msg->value_zone, &handle_zone_to_name_it, &ztn_ctx);
1156 GNUNET_SERVER_receive_done (client, GNUNET_OK);
1159 struct ZoneIterationProcResult
1162 struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded zone_key;
1165 struct GNUNET_CRYPTO_RsaSignature signature;
1166 struct GNUNET_TIME_Absolute expire;
1176 void zone_iteration_proc (void *cls,
1177 const struct GNUNET_CRYPTO_RsaPublicKeyBinaryEncoded *zone_key,
1178 struct GNUNET_TIME_Absolute expire,
1180 unsigned int rd_count,
1181 const struct GNUNET_NAMESTORE_RecordData *rd,
1182 const struct GNUNET_CRYPTO_RsaSignature *signature)
1184 struct GNUNET_NAMESTORE_ZoneIteration *zi = cls;
1185 struct GNUNET_NAMESTORE_Client *nc = zi->client;
1188 if ((zone_key == NULL) && (name == NULL))
1190 struct ZoneIterationResponseMessage zir_msg;
1191 if (zi->has_zone == GNUNET_YES)
1192 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "No more results for zone `%s'\n", GNUNET_h2s(&zi->zone));
1194 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "No more results for all zones\n");
1196 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending empty `%s' message\n", "ZONE_ITERATION_RESPONSE");
1197 zir_msg.gns_header.header.type = htons (GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_ITERATION_RESPONSE);
1198 zir_msg.gns_header.header.size = htons (sizeof (struct ZoneIterationResponseMessage));
1199 zir_msg.gns_header.r_id = htonl(zi->request_id);
1200 zir_msg.expire = GNUNET_TIME_absolute_hton(GNUNET_TIME_absolute_get_zero());
1201 zir_msg.name_len = htons (0);
1202 zir_msg.reserved = htons (0);
1203 zir_msg.rd_count = htons (0);
1204 zir_msg.rd_len = htons (0);
1205 memset (&zir_msg.public_key, '\0', sizeof (zir_msg.public_key));
1206 memset (&zir_msg.signature, '\0', sizeof (zir_msg.signature));
1207 GNUNET_SERVER_notification_context_unicast (snc, nc->client, (const struct GNUNET_MessageHeader *) &zir_msg, GNUNET_NO);
1209 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Removing zone iterator\n");
1210 GNUNET_CONTAINER_DLL_remove (nc->op_head, nc->op_tail, zi);
1216 struct ZoneIterationResponseMessage *zir_msg;
1217 if (zi->has_zone == GNUNET_YES)
1218 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending name `%s' for iteration over zone `%s'\n",
1219 name, GNUNET_h2s(&zi->zone));
1220 if (zi->has_zone == GNUNET_NO)
1221 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending name `%s' for iteration over all zones\n",
1229 name_len = strlen (name) +1;
1231 rd_ser_len = GNUNET_NAMESTORE_records_get_size(rd_count, rd);
1232 char rd_ser[rd_ser_len];
1233 GNUNET_NAMESTORE_records_serialize(rd_count, rd, rd_ser_len, rd_ser);
1234 msg_size = sizeof (struct ZoneIterationResponseMessage) + name_len + rd_ser_len;
1235 zir_msg = GNUNET_malloc(msg_size);
1237 name_tmp = (char *) &zir_msg[1];
1238 rd_tmp = &name_tmp[name_len];
1240 zir_msg->gns_header.header.type = htons (GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_ITERATION_RESPONSE);
1241 zir_msg->gns_header.header.size = htons (msg_size);
1242 zir_msg->gns_header.r_id = htonl(zi->request_id);
1243 zir_msg->expire = GNUNET_TIME_absolute_hton(expire);
1244 zir_msg->reserved = htons (0);
1245 zir_msg->name_len = htons (name_len);
1246 zir_msg->rd_count = htons (rd_count);
1247 zir_msg->rd_len = htons (rd_ser_len);
1248 zir_msg->signature = *signature;
1249 zir_msg->public_key = *zone_key;
1250 memcpy (name_tmp, name, name_len);
1251 memcpy (rd_tmp, rd_ser, rd_ser_len);
1253 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Sending empty `%s' message with size %u\n", "ZONE_ITERATION_RESPONSE", msg_size);
1254 GNUNET_SERVER_notification_context_unicast (snc, nc->client, (const struct GNUNET_MessageHeader *) zir_msg, GNUNET_NO);
1255 GNUNET_free (zir_msg);
1259 static void handle_iteration_start (void *cls,
1260 struct GNUNET_SERVER_Client * client,
1261 const struct GNUNET_MessageHeader * message)
1263 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received `%s' message\n", "ZONE_ITERATION_START");
1265 struct ZoneIterationStartMessage * zis_msg = (struct ZoneIterationStartMessage *) message;
1266 struct GNUNET_NAMESTORE_Client *nc;
1267 struct GNUNET_NAMESTORE_ZoneIteration *zi;
1270 nc = client_lookup(client);
1273 GNUNET_break_op (0);
1274 GNUNET_SERVER_receive_done (client, GNUNET_OK);
1278 zi = GNUNET_malloc (sizeof (struct GNUNET_NAMESTORE_ZoneIteration));
1279 zi->request_id = ntohl (zis_msg->gns_header.r_id);
1282 zi->zone = zis_msg->zone;
1284 GNUNET_HashCode dummy;
1285 GNUNET_HashCode *zone_tmp;
1286 memset (&dummy, '\0', sizeof (dummy));
1287 if (0 == memcmp (&dummy, &zis_msg->zone, sizeof (dummy)))
1289 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Starting to iterate over all zones\n");
1290 zi->has_zone = GNUNET_NO;
1295 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Starting to iterate over zone `%s'\n", GNUNET_h2s (&zis_msg->zone));
1296 zi->has_zone = GNUNET_YES;
1297 zone_tmp = &zis_msg->zone;
1300 GNUNET_CONTAINER_DLL_insert (nc->op_head, nc->op_tail, zi);
1302 res = GSN_database->iterate_records (GSN_database->cls, zone_tmp , NULL, zi->offset , &zone_iteration_proc, zi);
1303 GNUNET_SERVER_receive_done (client, GNUNET_OK);
1306 static void handle_iteration_stop (void *cls,
1307 struct GNUNET_SERVER_Client * client,
1308 const struct GNUNET_MessageHeader * message)
1310 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received `%s' message\n", "ZONE_ITERATION_STOP");
1312 struct GNUNET_NAMESTORE_Client *nc;
1313 struct GNUNET_NAMESTORE_ZoneIteration *zi;
1314 struct ZoneIterationStopMessage * zis_msg = (struct ZoneIterationStopMessage *) message;
1317 nc = client_lookup(client);
1320 GNUNET_break_op (0);
1321 GNUNET_SERVER_receive_done (client, GNUNET_OK);
1325 rid = ntohl (zis_msg->gns_header.r_id);
1326 for (zi = nc->op_head; zi != NULL; zi = zi->next)
1328 if (zi->request_id == rid)
1333 GNUNET_break_op (0);
1334 GNUNET_SERVER_receive_done (client, GNUNET_OK);
1338 GNUNET_CONTAINER_DLL_remove(nc->op_head, nc->op_tail, zi);
1339 if (GNUNET_YES == zi->has_zone)
1340 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stopped zone iteration for zone `%s'\n", GNUNET_h2s (&zi->zone));
1342 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stopped zone iteration all zones\n");
1345 GNUNET_SERVER_receive_done (client, GNUNET_OK);
1348 static void handle_iteration_next (void *cls,
1349 struct GNUNET_SERVER_Client * client,
1350 const struct GNUNET_MessageHeader * message)
1352 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received `%s' message\n", "ZONE_ITERATION_NEXT");
1354 struct GNUNET_NAMESTORE_Client *nc;
1355 struct GNUNET_NAMESTORE_ZoneIteration *zi;
1356 GNUNET_HashCode *zone_tmp;
1357 struct ZoneIterationStopMessage * zis_msg = (struct ZoneIterationStopMessage *) message;
1360 nc = client_lookup(client);
1363 GNUNET_break_op (0);
1364 GNUNET_SERVER_receive_done (client, GNUNET_OK);
1368 rid = ntohl (zis_msg->gns_header.r_id);
1369 for (zi = nc->op_head; zi != NULL; zi = zi->next)
1371 if (zi->request_id == rid)
1376 GNUNET_break_op (0);
1377 GNUNET_SERVER_receive_done (client, GNUNET_OK);
1381 if (GNUNET_YES == zi->has_zone)
1382 zone_tmp = &zi->zone;
1387 GSN_database->iterate_records (GSN_database->cls, zone_tmp, NULL, zi->offset , &zone_iteration_proc, zi);
1388 GNUNET_SERVER_receive_done (client, GNUNET_OK);
1394 * Process template requests.
1396 * @param cls closure
1397 * @param server the initialized server
1398 * @param cfg configuration to use
1401 run (void *cls, struct GNUNET_SERVER_Handle *server,
1402 const struct GNUNET_CONFIGURATION_Handle *cfg)
1406 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Starting namestore service\n");
1408 static const struct GNUNET_SERVER_MessageHandler handlers[] = {
1409 {&handle_start, NULL,
1410 GNUNET_MESSAGE_TYPE_NAMESTORE_START, sizeof (struct StartMessage)},
1411 {&handle_lookup_name, NULL,
1412 GNUNET_MESSAGE_TYPE_NAMESTORE_LOOKUP_NAME, 0},
1413 {&handle_record_put, NULL,
1414 GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_PUT, 0},
1415 {&handle_record_create, NULL,
1416 GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_CREATE, 0},
1417 {&handle_record_remove, NULL,
1418 GNUNET_MESSAGE_TYPE_NAMESTORE_RECORD_REMOVE, 0},
1419 {&handle_zone_to_name, NULL,
1420 GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_TO_NAME, 0},
1421 {&handle_iteration_start, NULL,
1422 GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_ITERATION_START, sizeof (struct ZoneIterationStartMessage)},
1423 {&handle_iteration_next, NULL,
1424 GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_ITERATION_NEXT, 0},
1425 {&handle_iteration_stop, NULL,
1426 GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_ITERATION_STOP, 0},
1432 /* Loading database plugin */
1434 GNUNET_CONFIGURATION_get_value_string (cfg, "namestore", "database",
1436 GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "No database backend configured\n");
1438 GNUNET_asprintf (&db_lib_name, "libgnunet_plugin_namestore_%s", database);
1439 GSN_database = GNUNET_PLUGIN_load (db_lib_name, (void *) GSN_cfg);
1440 if (GSN_database == NULL)
1441 GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Could not load database backend `%s'\n",
1443 GNUNET_free (database);
1445 /* Configuring server handles */
1446 GNUNET_SERVER_add_handlers (server, handlers);
1447 snc = GNUNET_SERVER_notification_context_create (server, 16);
1448 GNUNET_SERVER_disconnect_notify (server,
1449 &client_disconnect_notification,
1452 GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_FOREVER_REL, &cleanup_task,
1459 * The main function for the template service.
1461 * @param argc number of arguments from the command line
1462 * @param argv command line arguments
1463 * @return 0 ok, 1 on error
1466 main (int argc, char *const *argv)
1468 return (GNUNET_OK ==
1469 GNUNET_SERVICE_run (argc, argv, "namestore",
1470 GNUNET_SERVICE_OPTION_NONE, &run, NULL)) ? 0 : 1;
1473 /* end of gnunet-service-namestore.c */