aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorChristian Grothoff <christian@grothoff.org>2013-07-09 09:13:40 +0000
committerChristian Grothoff <christian@grothoff.org>2013-07-09 09:13:40 +0000
commitdea72e1e1b8173ac648778f0b2c2c2981e217b36 (patch)
treebc008e54d1f01c61fcaf05986d15dc692c66644e /src
parentaeb4a74b437e40384437dc93c7d58ea117bca07c (diff)
downloadgnunet-dea72e1e1b8173ac648778f0b2c2c2981e217b36.tar.gz
gnunet-dea72e1e1b8173ac648778f0b2c2c2981e217b36.zip
-towards implementing monitor functions in service
Diffstat (limited to 'src')
-rw-r--r--src/namestore/gnunet-service-namestore.c401
-rw-r--r--src/namestore/namestore_api.c5
-rw-r--r--src/namestore/plugin_namestore_sqlite.c4
3 files changed, 344 insertions, 66 deletions
diff --git a/src/namestore/gnunet-service-namestore.c b/src/namestore/gnunet-service-namestore.c
index 984c468fa..ffb799d76 100644
--- a/src/namestore/gnunet-service-namestore.c
+++ b/src/namestore/gnunet-service-namestore.c
@@ -34,25 +34,32 @@
34 34
35#define LOG_STRERROR_FILE(kind,syscall,filename) GNUNET_log_from_strerror_file (kind, "util", syscall, filename) 35#define LOG_STRERROR_FILE(kind,syscall,filename) GNUNET_log_from_strerror_file (kind, "util", syscall, filename)
36 36
37
38/**
39 * A namestore client
40 */
41struct NamestoreClient;
42
43
37/** 44/**
38 * A namestore operation. 45 * A namestore iteration operation.
39 */ 46 */
40struct GNUNET_NAMESTORE_ZoneIteration 47struct ZoneIteration
41{ 48{
42 /** 49 /**
43 * Next element in the DLL 50 * Next element in the DLL
44 */ 51 */
45 struct GNUNET_NAMESTORE_ZoneIteration *next; 52 struct ZoneIteration *next;
46 53
47 /** 54 /**
48 * Previous element in the DLL 55 * Previous element in the DLL
49 */ 56 */
50 struct GNUNET_NAMESTORE_ZoneIteration *prev; 57 struct ZoneIteration *prev;
51 58
52 /** 59 /**
53 * Namestore client which intiated this zone iteration 60 * Namestore client which intiated this zone iteration
54 */ 61 */
55 struct GNUNET_NAMESTORE_Client *client; 62 struct NamestoreClient *client;
56 63
57 /** 64 /**
58 * GNUNET_YES if we iterate over a specific zone 65 * GNUNET_YES if we iterate over a specific zone
@@ -95,17 +102,17 @@ struct GNUNET_NAMESTORE_ZoneIteration
95/** 102/**
96 * A namestore client 103 * A namestore client
97 */ 104 */
98struct GNUNET_NAMESTORE_Client 105struct NamestoreClient
99{ 106{
100 /** 107 /**
101 * Next element in the DLL 108 * Next element in the DLL
102 */ 109 */
103 struct GNUNET_NAMESTORE_Client *next; 110 struct NamestoreClient *next;
104 111
105 /** 112 /**
106 * Previous element in the DLL 113 * Previous element in the DLL
107 */ 114 */
108 struct GNUNET_NAMESTORE_Client *prev; 115 struct NamestoreClient *prev;
109 116
110 /** 117 /**
111 * The client 118 * The client
@@ -116,13 +123,13 @@ struct GNUNET_NAMESTORE_Client
116 * Head of the DLL of 123 * Head of the DLL of
117 * Zone iteration operations in progress initiated by this client 124 * Zone iteration operations in progress initiated by this client
118 */ 125 */
119 struct GNUNET_NAMESTORE_ZoneIteration *op_head; 126 struct ZoneIteration *op_head;
120 127
121 /** 128 /**
122 * Tail of the DLL of 129 * Tail of the DLL of
123 * Zone iteration operations in progress initiated by this client 130 * Zone iteration operations in progress initiated by this client
124 */ 131 */
125 struct GNUNET_NAMESTORE_ZoneIteration *op_tail; 132 struct ZoneIteration *op_tail;
126}; 133};
127 134
128 135
@@ -150,6 +157,62 @@ struct GNUNET_NAMESTORE_CryptoContainer
150 157
151 158
152/** 159/**
160 * A namestore monitor.
161 */
162struct ZoneMonitor
163{
164 /**
165 * Next element in the DLL
166 */
167 struct ZoneMonitor *next;
168
169 /**
170 * Previous element in the DLL
171 */
172 struct ZoneMonitor *prev;
173
174 /**
175 * Namestore client which intiated this zone monitor
176 */
177 struct GNUNET_SERVER_Client *client;
178
179 /**
180 * GNUNET_YES if we monitor over a specific zone
181 * GNUNET_NO if we monitor all zones
182 */
183 int has_zone;
184
185 /**
186 * Hash of the specific zone if 'has_zone' is GNUNET_YES,
187 * othwerwise set to '\0'
188 */
189 struct GNUNET_CRYPTO_ShortHashCode zone;
190
191 /**
192 * The operation id fot the zone iteration in the response for the client
193 */
194 uint64_t request_id;
195
196 /**
197 * Task active during initial iteration.
198 */
199 GNUNET_SCHEDULER_TaskIdentifier task;
200
201 /**
202 * Offset of the zone iteration used to address next result of the zone
203 * iteration in the store
204 *
205 * Initialy set to 0 in handle_iteration_start
206 * Incremented with by every call to handle_iteration_next
207 */
208 uint32_t offset;
209
210};
211
212
213
214
215/**
153 * Configuration handle. 216 * Configuration handle.
154 */ 217 */
155static const struct GNUNET_CONFIGURATION_Handle *GSN_cfg; 218static const struct GNUNET_CONFIGURATION_Handle *GSN_cfg;
@@ -177,12 +240,12 @@ static struct GNUNET_SERVER_NotificationContext *snc;
177/** 240/**
178 * Head of the Client DLL 241 * Head of the Client DLL
179 */ 242 */
180static struct GNUNET_NAMESTORE_Client *client_head; 243static struct NamestoreClient *client_head;
181 244
182/** 245/**
183 * Tail of the Client DLL 246 * Tail of the Client DLL
184 */ 247 */
185static struct GNUNET_NAMESTORE_Client *client_tail; 248static struct NamestoreClient *client_tail;
186 249
187/** 250/**
188 * Hashmap containing the zone keys this namestore has is authoritative for 251 * Hashmap containing the zone keys this namestore has is authoritative for
@@ -192,6 +255,21 @@ static struct GNUNET_NAMESTORE_Client *client_tail;
192 */ 255 */
193static struct GNUNET_CONTAINER_MultiHashMap *zonekeys; 256static struct GNUNET_CONTAINER_MultiHashMap *zonekeys;
194 257
258/**
259 * First active zone monitor.
260 */
261static struct ZoneMonitor *monitor_head;
262
263/**
264 * Last active zone monitor.
265 */
266static struct ZoneMonitor *monitor_tail;
267
268/**
269 * Notification context shared by all monitors.
270 */
271static struct GNUNET_SERVER_NotificationContext *monitor_nc;
272
195 273
196/** 274/**
197 * Writes the encrypted private key of a zone in a file 275 * Writes the encrypted private key of a zone in a file
@@ -226,7 +304,9 @@ write_key_to_file (const char *filename,
226 return GNUNET_SYSERR; 304 return GNUNET_SYSERR;
227 } 305 }
228 GNUNET_CRYPTO_ecc_key_get_public (privkey, &pubkey); 306 GNUNET_CRYPTO_ecc_key_get_public (privkey, &pubkey);
229 GNUNET_CRYPTO_short_hash (&pubkey, sizeof (struct GNUNET_CRYPTO_EccPublicKeyBinaryEncoded), &zone); 307 GNUNET_CRYPTO_short_hash (&pubkey,
308 sizeof (struct GNUNET_CRYPTO_EccPublicKeyBinaryEncoded),
309 &zone);
230 GNUNET_CRYPTO_ecc_key_free (privkey); 310 GNUNET_CRYPTO_ecc_key_free (privkey);
231 if (0 == memcmp (&zone, &c->zone, sizeof(zone))) 311 if (0 == memcmp (&zone, &c->zone, sizeof(zone)))
232 { 312 {
@@ -381,8 +461,8 @@ get_block_expiration_time (unsigned int rd_count, const struct GNUNET_NAMESTORE_
381static void 461static void
382cleanup_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc) 462cleanup_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc)
383{ 463{
384 struct GNUNET_NAMESTORE_ZoneIteration *no; 464 struct ZoneIteration *no;
385 struct GNUNET_NAMESTORE_Client *nc; 465 struct NamestoreClient *nc;
386 466
387 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stopping namestore service\n"); 467 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Stopping namestore service\n");
388 if (NULL != snc) 468 if (NULL != snc)
@@ -408,6 +488,11 @@ cleanup_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc)
408 db_lib_name = NULL; 488 db_lib_name = NULL;
409 GNUNET_free_non_null (zonefile_directory); 489 GNUNET_free_non_null (zonefile_directory);
410 zonefile_directory = NULL; 490 zonefile_directory = NULL;
491 if (NULL != monitor_nc)
492 {
493 GNUNET_SERVER_notification_context_destroy (monitor_nc);
494 monitor_nc = NULL;
495 }
411} 496}
412 497
413 498
@@ -418,10 +503,10 @@ cleanup_task (void *cls, const struct GNUNET_SCHEDULER_TaskContext *tc)
418 * @return our internal structure for the client, NULL if 503 * @return our internal structure for the client, NULL if
419 * we do not have any yet 504 * we do not have any yet
420 */ 505 */
421static struct GNUNET_NAMESTORE_Client * 506static struct NamestoreClient *
422client_lookup (struct GNUNET_SERVER_Client *client) 507client_lookup (struct GNUNET_SERVER_Client *client)
423{ 508{
424 struct GNUNET_NAMESTORE_Client *nc; 509 struct NamestoreClient *nc;
425 510
426 GNUNET_assert (NULL != client); 511 GNUNET_assert (NULL != client);
427 for (nc = client_head; NULL != nc; nc = nc->next) 512 for (nc = client_head; NULL != nc; nc = nc->next)
@@ -442,8 +527,9 @@ static void
442client_disconnect_notification (void *cls, 527client_disconnect_notification (void *cls,
443 struct GNUNET_SERVER_Client *client) 528 struct GNUNET_SERVER_Client *client)
444{ 529{
445 struct GNUNET_NAMESTORE_ZoneIteration *no; 530 struct ZoneIteration *no;
446 struct GNUNET_NAMESTORE_Client *nc; 531 struct NamestoreClient *nc;
532 struct ZoneMonitor *zm;
447 533
448 if (NULL == client) 534 if (NULL == client)
449 return; 535 return;
@@ -459,6 +545,22 @@ client_disconnect_notification (void *cls,
459 } 545 }
460 GNUNET_CONTAINER_DLL_remove (client_head, client_tail, nc); 546 GNUNET_CONTAINER_DLL_remove (client_head, client_tail, nc);
461 GNUNET_free (nc); 547 GNUNET_free (nc);
548 for (zm = monitor_head; NULL != zm; zm = zm->next)
549 {
550 if (client == zm->client)
551 {
552 GNUNET_CONTAINER_DLL_remove (monitor_head,
553 monitor_tail,
554 zm);
555 if (GNUNET_SCHEDULER_NO_TASK != zm->task)
556 {
557 GNUNET_SCHEDULER_cancel (zm->task);
558 zm->task = GNUNET_SCHEDULER_NO_TASK;
559 }
560 GNUNET_free (zm);
561 break;
562 }
563 }
462} 564}
463 565
464 566
@@ -474,7 +576,7 @@ handle_start (void *cls,
474 struct GNUNET_SERVER_Client *client, 576 struct GNUNET_SERVER_Client *client,
475 const struct GNUNET_MessageHeader *message) 577 const struct GNUNET_MessageHeader *message)
476{ 578{
477 struct GNUNET_NAMESTORE_Client *nc; 579 struct NamestoreClient *nc;
478 580
479 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, 581 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
480 "Client %p connected\n", client); 582 "Client %p connected\n", client);
@@ -484,7 +586,7 @@ handle_start (void *cls,
484 GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); 586 GNUNET_SERVER_receive_done (client, GNUNET_SYSERR);
485 return; 587 return;
486 } 588 }
487 nc = GNUNET_malloc (sizeof (struct GNUNET_NAMESTORE_Client)); 589 nc = GNUNET_malloc (sizeof (struct NamestoreClient));
488 nc->client = client; 590 nc->client = client;
489 GNUNET_SERVER_notification_context_add (snc, client); 591 GNUNET_SERVER_notification_context_add (snc, client);
490 GNUNET_CONTAINER_DLL_insert (client_head, client_tail, nc); 592 GNUNET_CONTAINER_DLL_insert (client_head, client_tail, nc);
@@ -501,7 +603,7 @@ struct LookupNameContext
501 /** 603 /**
502 * The client to send the response to 604 * The client to send the response to
503 */ 605 */
504 struct GNUNET_NAMESTORE_Client *nc; 606 struct NamestoreClient *nc;
505 607
506 /** 608 /**
507 * Requested zone 609 * Requested zone
@@ -696,7 +798,6 @@ handle_lookup_name_it (void *cls,
696 rd_ser_len = GNUNET_NAMESTORE_records_get_size (copied_elements, rd_selected); 798 rd_ser_len = GNUNET_NAMESTORE_records_get_size (copied_elements, rd_selected);
697 name_len = (NULL == name) ? 0 : strlen(name) + 1; 799 name_len = (NULL == name) ? 0 : strlen(name) + 1;
698 r_size = sizeof (struct LookupNameResponseMessage) + 800 r_size = sizeof (struct LookupNameResponseMessage) +
699 sizeof (struct GNUNET_CRYPTO_EccPublicKeyBinaryEncoded) +
700 name_len + 801 name_len +
701 rd_ser_len; 802 rd_ser_len;
702 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, 803 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
@@ -743,6 +844,31 @@ handle_lookup_name_it (void *cls,
743 844
744 845
745/** 846/**
847 * Send an empty name response to indicate the end of the
848 * set of results to the client.
849 *
850 * @param nc notification context to use for sending
851 * @param client destination of the empty response
852 * @param request_id identification for the request
853 */
854static void
855send_empty_response (struct GNUNET_SERVER_NotificationContext *nc,
856 struct GNUNET_SERVER_Client *client,
857 uint32_t request_id)
858{
859 struct LookupNameResponseMessage zir_end;
860
861 memset (&zir_end, 0, sizeof (zir_end));
862 zir_end.gns_header.header.type = htons (GNUNET_MESSAGE_TYPE_NAMESTORE_LOOKUP_NAME_RESPONSE);
863 zir_end.gns_header.header.size = htons (sizeof (struct LookupNameResponseMessage));
864 zir_end.gns_header.r_id = htonl(request_id);
865 GNUNET_SERVER_notification_context_unicast (nc,
866 client,
867 &zir_end.gns_header.header, GNUNET_NO);
868}
869
870
871/**
746 * Handles a 'GNUNET_MESSAGE_TYPE_NAMESTORE_LOOKUP_NAME' message 872 * Handles a 'GNUNET_MESSAGE_TYPE_NAMESTORE_LOOKUP_NAME' message
747 * 873 *
748 * @param cls unused 874 * @param cls unused
@@ -756,12 +882,13 @@ handle_lookup_name (void *cls,
756{ 882{
757 const struct LookupNameMessage *ln_msg; 883 const struct LookupNameMessage *ln_msg;
758 struct LookupNameContext lnc; 884 struct LookupNameContext lnc;
759 struct GNUNET_NAMESTORE_Client *nc; 885 struct NamestoreClient *nc;
760 size_t name_len; 886 size_t name_len;
761 const char *name; 887 const char *name;
762 uint32_t rid; 888 uint32_t rid;
763 uint32_t type; 889 uint32_t type;
764 char *conv_name; 890 char *conv_name;
891 int ret;
765 892
766 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, 893 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
767 "Received `%s' message\n", 894 "Received `%s' message\n",
@@ -789,7 +916,7 @@ handle_lookup_name (void *cls,
789 return; 916 return;
790 } 917 }
791 name = (const char *) &ln_msg[1]; 918 name = (const char *) &ln_msg[1];
792 if ('\0' != name[name_len -1]) 919 if ('\0' != name[name_len - 1])
793 { 920 {
794 GNUNET_break (0); 921 GNUNET_break (0);
795 GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); 922 GNUNET_SERVER_receive_done (client, GNUNET_SYSERR);
@@ -809,9 +936,9 @@ handle_lookup_name (void *cls,
809 conv_name = GNUNET_NAMESTORE_normalize_string (name); 936 conv_name = GNUNET_NAMESTORE_normalize_string (name);
810 if (NULL == conv_name) 937 if (NULL == conv_name)
811 { 938 {
812 GNUNET_log (GNUNET_ERROR_TYPE_ERROR, 939 GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
813 "Error converting name `%s'\n", name); 940 "Error converting name `%s'\n", name);
814 return; 941 return;
815 } 942 }
816 943
817 /* do the actual lookup */ 944 /* do the actual lookup */
@@ -821,9 +948,9 @@ handle_lookup_name (void *cls,
821 lnc.name = conv_name; 948 lnc.name = conv_name;
822 lnc.zone = &ln_msg->zone; 949 lnc.zone = &ln_msg->zone;
823 if (GNUNET_SYSERR == 950 if (GNUNET_SYSERR ==
824 GSN_database->iterate_records (GSN_database->cls, 951 (ret = GSN_database->iterate_records (GSN_database->cls,
825 &ln_msg->zone, conv_name, 0 /* offset */, 952 &ln_msg->zone, conv_name, 0 /* offset */,
826 &handle_lookup_name_it, &lnc)) 953 &handle_lookup_name_it, &lnc)))
827 { 954 {
828 /* internal error (in database plugin); might be best to just hang up on 955 /* internal error (in database plugin); might be best to just hang up on
829 plugin rather than to signal that there are 'no' results, which 956 plugin rather than to signal that there are 'no' results, which
@@ -832,8 +959,13 @@ handle_lookup_name (void *cls,
832 GNUNET_SERVER_receive_done (client, GNUNET_SYSERR); 959 GNUNET_SERVER_receive_done (client, GNUNET_SYSERR);
833 GNUNET_free (conv_name); 960 GNUNET_free (conv_name);
834 return; 961 return;
835 } 962 }
836 GNUNET_free (conv_name); 963 GNUNET_free (conv_name);
964 if (0 == ret)
965 {
966 /* no records match at all, generate empty response */
967 send_empty_response (snc, nc->client, rid);
968 }
837 GNUNET_SERVER_receive_done (client, GNUNET_OK); 969 GNUNET_SERVER_receive_done (client, GNUNET_OK);
838} 970}
839 971
@@ -850,7 +982,7 @@ handle_record_put (void *cls,
850 struct GNUNET_SERVER_Client *client, 982 struct GNUNET_SERVER_Client *client,
851 const struct GNUNET_MessageHeader *message) 983 const struct GNUNET_MessageHeader *message)
852{ 984{
853 struct GNUNET_NAMESTORE_Client *nc; 985 struct NamestoreClient *nc;
854 const struct RecordPutMessage *rp_msg; 986 const struct RecordPutMessage *rp_msg;
855 struct GNUNET_TIME_Absolute expire; 987 struct GNUNET_TIME_Absolute expire;
856 const struct GNUNET_CRYPTO_EccSignature *signature; 988 const struct GNUNET_CRYPTO_EccSignature *signature;
@@ -975,7 +1107,7 @@ handle_record_create (void *cls,
975 const struct GNUNET_MessageHeader *message) 1107 const struct GNUNET_MessageHeader *message)
976{ 1108{
977 static struct GNUNET_CRYPTO_EccSignature dummy_signature; 1109 static struct GNUNET_CRYPTO_EccSignature dummy_signature;
978 struct GNUNET_NAMESTORE_Client *nc; 1110 struct NamestoreClient *nc;
979 const struct RecordCreateMessage *rp_msg; 1111 const struct RecordCreateMessage *rp_msg;
980 struct GNUNET_CRYPTO_EccPrivateKey *pkey; 1112 struct GNUNET_CRYPTO_EccPrivateKey *pkey;
981 struct RecordCreateResponseMessage rcr_msg; 1113 struct RecordCreateResponseMessage rcr_msg;
@@ -1113,7 +1245,7 @@ struct ZoneToNameCtx
1113 /** 1245 /**
1114 * Namestore client 1246 * Namestore client
1115 */ 1247 */
1116 struct GNUNET_NAMESTORE_Client *nc; 1248 struct NamestoreClient *nc;
1117 1249
1118 /** 1250 /**
1119 * Request id (to be used in the response to the client). 1251 * Request id (to be used in the response to the client).
@@ -1228,7 +1360,7 @@ handle_zone_to_name (void *cls,
1228 struct GNUNET_SERVER_Client *client, 1360 struct GNUNET_SERVER_Client *client,
1229 const struct GNUNET_MessageHeader *message) 1361 const struct GNUNET_MessageHeader *message)
1230{ 1362{
1231 struct GNUNET_NAMESTORE_Client *nc; 1363 struct NamestoreClient *nc;
1232 const struct ZoneToNameMessage *ztn_msg; 1364 const struct ZoneToNameMessage *ztn_msg;
1233 struct ZoneToNameCtx ztn_ctx; 1365 struct ZoneToNameCtx ztn_ctx;
1234 1366
@@ -1294,7 +1426,7 @@ struct ZoneIterationProcResult
1294 /** 1426 /**
1295 * The zone iteration handle 1427 * The zone iteration handle
1296 */ 1428 */
1297 struct GNUNET_NAMESTORE_ZoneIteration *zi; 1429 struct ZoneIteration *zi;
1298 1430
1299 /** 1431 /**
1300 * Iteration result: iteration done? 1432 * Iteration result: iteration done?
@@ -1436,7 +1568,7 @@ zone_iteraterate_proc (void *cls,
1436 } 1568 }
1437 } 1569 }
1438 } 1570 }
1439 if (rd_count_filtered == 0) 1571 if (0 == rd_count_filtered)
1440 { 1572 {
1441 /* After filtering records there are no records left to return */ 1573 /* After filtering records there are no records left to return */
1442 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "No records to transmit\n"); 1574 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "No records to transmit\n");
@@ -1476,8 +1608,9 @@ zone_iteraterate_proc (void *cls,
1476 "Sending `%s' message with size %u\n", 1608 "Sending `%s' message with size %u\n",
1477 "ZONE_ITERATION_RESPONSE", 1609 "ZONE_ITERATION_RESPONSE",
1478 msg_size); 1610 msg_size);
1479 GNUNET_SERVER_notification_context_unicast (snc, proc->zi->client->client, 1611 GNUNET_SERVER_notification_context_unicast (snc,
1480 (const struct GNUNET_MessageHeader *) zir_msg, 1612 proc->zi->client->client,
1613 &zir_msg->gns_header.header,
1481 GNUNET_NO); 1614 GNUNET_NO);
1482 proc->res_iteration_finished = IT_SUCCESS_MORE_AVAILABLE; 1615 proc->res_iteration_finished = IT_SUCCESS_MORE_AVAILABLE;
1483 GNUNET_free (zir_msg); 1616 GNUNET_free (zir_msg);
@@ -1491,11 +1624,11 @@ zone_iteraterate_proc (void *cls,
1491 * @param zi zone iterator to process 1624 * @param zi zone iterator to process
1492 */ 1625 */
1493static void 1626static void
1494run_zone_iteration_round (struct GNUNET_NAMESTORE_ZoneIteration *zi) 1627run_zone_iteration_round (struct ZoneIteration *zi)
1495{ 1628{
1496 struct ZoneIterationProcResult proc; 1629 struct ZoneIterationProcResult proc;
1497 struct LookupNameResponseMessage zir_end;
1498 struct GNUNET_CRYPTO_ShortHashCode *zone; 1630 struct GNUNET_CRYPTO_ShortHashCode *zone;
1631 int ret;
1499 1632
1500 memset (&proc, 0, sizeof (proc)); 1633 memset (&proc, 0, sizeof (proc));
1501 proc.zi = zi; 1634 proc.zi = zi;
@@ -1507,13 +1640,15 @@ run_zone_iteration_round (struct GNUNET_NAMESTORE_ZoneIteration *zi)
1507 while (IT_ALL_RECORDS_FILTERED == proc.res_iteration_finished) 1640 while (IT_ALL_RECORDS_FILTERED == proc.res_iteration_finished)
1508 { 1641 {
1509 if (GNUNET_SYSERR == 1642 if (GNUNET_SYSERR ==
1510 GSN_database->iterate_records (GSN_database->cls, zone, NULL, 1643 (ret = GSN_database->iterate_records (GSN_database->cls, zone, NULL,
1511 zi->offset, 1644 zi->offset,
1512 &zone_iteraterate_proc, &proc)) 1645 &zone_iteraterate_proc, &proc)))
1513 { 1646 {
1514 GNUNET_break (0); 1647 GNUNET_break (0);
1515 break; 1648 break;
1516 } 1649 }
1650 if (GNUNET_NO == ret)
1651 proc.res_iteration_finished = IT_SUCCESS_NOT_MORE_RESULTS_AVAILABLE;
1517 zi->offset++; 1652 zi->offset++;
1518 } 1653 }
1519 if (IT_SUCCESS_MORE_AVAILABLE == proc.res_iteration_finished) 1654 if (IT_SUCCESS_MORE_AVAILABLE == proc.res_iteration_finished)
@@ -1529,16 +1664,12 @@ run_zone_iteration_round (struct GNUNET_NAMESTORE_ZoneIteration *zi)
1529 else 1664 else
1530 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, 1665 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
1531 "No more results for all zones\n"); 1666 "No more results for all zones\n");
1532 memset (&zir_end, 0, sizeof (zir_end)); 1667 send_empty_response (snc, zi->client->client, zi->request_id);
1533 zir_end.gns_header.header.type = htons (GNUNET_MESSAGE_TYPE_NAMESTORE_LOOKUP_NAME_RESPONSE);
1534 zir_end.gns_header.header.size = htons (sizeof (struct LookupNameResponseMessage));
1535 zir_end.gns_header.r_id = htonl(zi->request_id);
1536 GNUNET_SERVER_notification_context_unicast (snc,
1537 zi->client->client,
1538 &zir_end.gns_header.header, GNUNET_NO);
1539 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, 1668 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
1540 "Removing zone iterator\n"); 1669 "Removing zone iterator\n");
1541 GNUNET_CONTAINER_DLL_remove (zi->client->op_head, zi->client->op_tail, zi); 1670 GNUNET_CONTAINER_DLL_remove (zi->client->op_head,
1671 zi->client->op_tail,
1672 zi);
1542 GNUNET_free (zi); 1673 GNUNET_free (zi);
1543} 1674}
1544 1675
@@ -1557,8 +1688,8 @@ handle_iteration_start (void *cls,
1557{ 1688{
1558 static struct GNUNET_CRYPTO_ShortHashCode zeros; 1689 static struct GNUNET_CRYPTO_ShortHashCode zeros;
1559 const struct ZoneIterationStartMessage *zis_msg; 1690 const struct ZoneIterationStartMessage *zis_msg;
1560 struct GNUNET_NAMESTORE_Client *nc; 1691 struct NamestoreClient *nc;
1561 struct GNUNET_NAMESTORE_ZoneIteration *zi; 1692 struct ZoneIteration *zi;
1562 1693
1563 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received `%s' message\n", "ZONE_ITERATION_START"); 1694 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received `%s' message\n", "ZONE_ITERATION_START");
1564 if (NULL == (nc = client_lookup (client))) 1695 if (NULL == (nc = client_lookup (client)))
@@ -1568,7 +1699,7 @@ handle_iteration_start (void *cls,
1568 return; 1699 return;
1569 } 1700 }
1570 zis_msg = (const struct ZoneIterationStartMessage *) message; 1701 zis_msg = (const struct ZoneIterationStartMessage *) message;
1571 zi = GNUNET_malloc (sizeof (struct GNUNET_NAMESTORE_ZoneIteration)); 1702 zi = GNUNET_new (struct ZoneIteration);
1572 zi->request_id = ntohl (zis_msg->gns_header.r_id); 1703 zi->request_id = ntohl (zis_msg->gns_header.r_id);
1573 zi->offset = 0; 1704 zi->offset = 0;
1574 zi->client = nc; 1705 zi->client = nc;
@@ -1605,8 +1736,8 @@ handle_iteration_stop (void *cls,
1605 struct GNUNET_SERVER_Client *client, 1736 struct GNUNET_SERVER_Client *client,
1606 const struct GNUNET_MessageHeader *message) 1737 const struct GNUNET_MessageHeader *message)
1607{ 1738{
1608 struct GNUNET_NAMESTORE_Client *nc; 1739 struct NamestoreClient *nc;
1609 struct GNUNET_NAMESTORE_ZoneIteration *zi; 1740 struct ZoneIteration *zi;
1610 const struct ZoneIterationStopMessage *zis_msg; 1741 const struct ZoneIterationStopMessage *zis_msg;
1611 uint32_t rid; 1742 uint32_t rid;
1612 1743
@@ -1655,8 +1786,8 @@ handle_iteration_next (void *cls,
1655 struct GNUNET_SERVER_Client *client, 1786 struct GNUNET_SERVER_Client *client,
1656 const struct GNUNET_MessageHeader *message) 1787 const struct GNUNET_MessageHeader *message)
1657{ 1788{
1658 struct GNUNET_NAMESTORE_Client *nc; 1789 struct NamestoreClient *nc;
1659 struct GNUNET_NAMESTORE_ZoneIteration *zi; 1790 struct ZoneIteration *zi;
1660 const struct ZoneIterationNextMessage *zis_msg; 1791 const struct ZoneIterationNextMessage *zis_msg;
1661 uint32_t rid; 1792 uint32_t rid;
1662 1793
@@ -1708,6 +1839,148 @@ zonekey_file_it (void *cls, const char *filename)
1708 1839
1709 1840
1710/** 1841/**
1842 * Send 'sync' message to zone monitor, we're now in sync.
1843 *
1844 * @param zm monitor that is now in sync
1845 */
1846static void
1847monitor_sync (struct ZoneMonitor *zm)
1848{
1849 struct GNUNET_MessageHeader sync;
1850
1851 sync.size = htons (sizeof (struct GNUNET_MessageHeader));
1852 sync.type = htons (GNUNET_MESSAGE_TYPE_NAMESTORE_MONITOR_SYNC);
1853 GNUNET_SERVER_notification_context_unicast (monitor_nc,
1854 zm->client,
1855 &sync,
1856 GNUNET_NO);
1857}
1858
1859
1860/**
1861 * Obtain the next datum during the zone monitor's zone intiial iteration.
1862 *
1863 * @param cls zone monitor that does its initial iteration
1864 * @param tc scheduler context
1865 */
1866static void
1867monitor_next (void *cls,
1868 const struct GNUNET_SCHEDULER_TaskContext *tc);
1869
1870
1871/**
1872 * A 'GNUNET_NAMESTORE_RecordIterator' for monitors.
1873 *
1874 * @param cls a 'struct ZoneMonitor *' with information about the monitor
1875 * @param zone_key zone key of the zone
1876 * @param expire expiration time
1877 * @param name name
1878 * @param rd_count number of records
1879 * @param rd array of records
1880 * @param signature signature
1881 */
1882static void
1883monitor_iterate_cb (void *cls,
1884 const struct GNUNET_CRYPTO_EccPublicKeyBinaryEncoded *zone_key,
1885 struct GNUNET_TIME_Absolute expire,
1886 const char *name,
1887 unsigned int rd_count,
1888 const struct GNUNET_NAMESTORE_RecordData *rd,
1889 const struct GNUNET_CRYPTO_EccSignature *signature)
1890{
1891 struct ZoneMonitor *zm = cls;
1892
1893 if (NULL == name)
1894 {
1895 /* finished with iteration */
1896 monitor_sync (zm);
1897 return;
1898 }
1899 // FIXME: send message to client!
1900 zm->task = GNUNET_SCHEDULER_add_now (&monitor_next, zm);
1901}
1902
1903
1904/**
1905 * Handles a 'GNUNET_MESSAGE_TYPE_NAMESTORE_MONITOR_START' message
1906 *
1907 * @param cls unused
1908 * @param client GNUNET_SERVER_Client sending the message
1909 * @param message message of type 'struct ZoneMonitorStartMessage'
1910 */
1911static void
1912handle_monitor_start (void *cls,
1913 struct GNUNET_SERVER_Client *client,
1914 const struct GNUNET_MessageHeader *message)
1915{
1916 static struct GNUNET_CRYPTO_ShortHashCode zeros;
1917 const struct ZoneMonitorStartMessage *zis_msg;
1918 struct ZoneMonitor *zm;
1919
1920 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
1921 "Received `%s' message\n",
1922 "ZONE_MONITOR_START");
1923 zis_msg = (const struct ZoneMonitorStartMessage *) message;
1924 zm = GNUNET_new (struct ZoneMonitor);
1925 zm->request_id = ntohl (zis_msg->gns_header.r_id);
1926 zm->offset = 0;
1927 zm->client = client; // FIXME: notify handler for disconnects, check monitors!
1928 if (0 == memcmp (&zeros, &zis_msg->zone, sizeof (zeros)))
1929 {
1930 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
1931 "Starting to monitor all zones\n");
1932 zm->zone = zis_msg->zone;
1933 zm->has_zone = GNUNET_NO;
1934 }
1935 else
1936 {
1937 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG,
1938 "Starting to monitor zone `%s'\n",
1939 GNUNET_NAMESTORE_short_h2s (&zis_msg->zone));
1940 zm->zone = zis_msg->zone;
1941 zm->has_zone = GNUNET_YES;
1942 }
1943 GNUNET_CONTAINER_DLL_insert (monitor_head, monitor_tail, zm);
1944 GNUNET_SERVER_client_mark_monitor (client);
1945 GNUNET_SERVER_notification_context_add (monitor_nc,
1946 client);
1947 zm->task = GNUNET_SCHEDULER_add_now (&monitor_next, zm);
1948}
1949
1950
1951/**
1952 * Obtain the next datum during the zone monitor's zone intiial iteration.
1953 *
1954 * @param cls zone monitor that does its initial iteration
1955 * @param tc scheduler context
1956 */
1957static void
1958monitor_next (void *cls,
1959 const struct GNUNET_SCHEDULER_TaskContext *tc)
1960{
1961 struct ZoneMonitor *zm = cls;
1962 int ret;
1963
1964 zm->task = GNUNET_SCHEDULER_NO_TASK;
1965 ret = GSN_database->iterate_records (GSN_database->cls,
1966 (GNUNET_YES == zm->has_zone) ? &zm->zone : NULL,
1967 NULL, zm->offset++,
1968 &monitor_iterate_cb, zm);
1969 if (GNUNET_SYSERR == ret)
1970 {
1971 GNUNET_SERVER_client_disconnect (zm->client);
1972 return;
1973 }
1974 if (GNUNET_NO == ret)
1975 {
1976 /* empty zone */
1977 monitor_sync (zm);
1978 return;
1979 }
1980}
1981
1982
1983/**
1711 * Process namestore requests. 1984 * Process namestore requests.
1712 * 1985 *
1713 * @param cls closure 1986 * @param cls closure
@@ -1733,8 +2006,10 @@ run (void *cls, struct GNUNET_SERVER_Handle *server,
1733 GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_ITERATION_START, sizeof (struct ZoneIterationStartMessage) }, 2006 GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_ITERATION_START, sizeof (struct ZoneIterationStartMessage) },
1734 {&handle_iteration_next, NULL, 2007 {&handle_iteration_next, NULL,
1735 GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_ITERATION_NEXT, sizeof (struct ZoneIterationNextMessage) }, 2008 GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_ITERATION_NEXT, sizeof (struct ZoneIterationNextMessage) },
1736 {&handle_iteration_stop, NULL, 2009 {&handle_iteration_stop, NULL,
1737 GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_ITERATION_STOP, sizeof (struct ZoneIterationStopMessage) }, 2010 GNUNET_MESSAGE_TYPE_NAMESTORE_ZONE_ITERATION_STOP, sizeof (struct ZoneIterationStopMessage) },
2011 {&handle_monitor_start, NULL,
2012 GNUNET_MESSAGE_TYPE_NAMESTORE_MONITOR_START, sizeof (struct ZoneMonitorStartMessage) },
1738 {NULL, NULL, 0, 0} 2013 {NULL, NULL, 0, 0}
1739 }; 2014 };
1740 char *database; 2015 char *database;
@@ -1742,7 +2017,7 @@ run (void *cls, struct GNUNET_SERVER_Handle *server,
1742 2017
1743 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Starting namestore service\n"); 2018 GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Starting namestore service\n");
1744 GSN_cfg = cfg; 2019 GSN_cfg = cfg;
1745 2020 monitor_nc = GNUNET_SERVER_notification_context_create (server, 1);
1746 /* Load private keys from disk */ 2021 /* Load private keys from disk */
1747 if (GNUNET_OK != 2022 if (GNUNET_OK !=
1748 GNUNET_CONFIGURATION_get_value_filename (cfg, "namestore", 2023 GNUNET_CONFIGURATION_get_value_filename (cfg, "namestore",
diff --git a/src/namestore/namestore_api.c b/src/namestore/namestore_api.c
index 54cc8ec66..882770af2 100644
--- a/src/namestore/namestore_api.c
+++ b/src/namestore/namestore_api.c
@@ -274,7 +274,9 @@ handle_lookup_name_response (struct GNUNET_NAMESTORE_QueueEntry *qe,
274 int contains_sig; 274 int contains_sig;
275 int rd_count; 275 int rd_count;
276 276
277 LOG (GNUNET_ERROR_TYPE_DEBUG, "Received `%s'\n", "LOOKUP_NAME_RESPONSE"); 277 LOG (GNUNET_ERROR_TYPE_DEBUG,
278 "Received `%s'\n",
279 "LOOKUP_NAME_RESPONSE");
278 rd_len = ntohs (msg->rd_len); 280 rd_len = ntohs (msg->rd_len);
279 rd_count = ntohs (msg->rd_count); 281 rd_count = ntohs (msg->rd_count);
280 msg_len = ntohs (msg->gns_header.header.size); 282 msg_len = ntohs (msg->gns_header.header.size);
@@ -282,7 +284,6 @@ handle_lookup_name_response (struct GNUNET_NAMESTORE_QueueEntry *qe,
282 contains_sig = ntohs (msg->contains_sig); 284 contains_sig = ntohs (msg->contains_sig);
283 expire = GNUNET_TIME_absolute_ntoh (msg->expire); 285 expire = GNUNET_TIME_absolute_ntoh (msg->expire);
284 exp_msg_len = sizeof (struct LookupNameResponseMessage) + 286 exp_msg_len = sizeof (struct LookupNameResponseMessage) +
285 sizeof (struct GNUNET_CRYPTO_EccPublicKeyBinaryEncoded) +
286 name_len + rd_len; 287 name_len + rd_len;
287 if (msg_len != exp_msg_len) 288 if (msg_len != exp_msg_len)
288 { 289 {
diff --git a/src/namestore/plugin_namestore_sqlite.c b/src/namestore/plugin_namestore_sqlite.c
index 806debae4..6c76d12e9 100644
--- a/src/namestore/plugin_namestore_sqlite.c
+++ b/src/namestore/plugin_namestore_sqlite.c
@@ -683,7 +683,9 @@ namestore_sqlite_iterate_records (void *cls,
683 &name_hase, sizeof (struct GNUNET_CRYPTO_ShortHashCode), 683 &name_hase, sizeof (struct GNUNET_CRYPTO_ShortHashCode),
684 SQLITE_STATIC)) ) 684 SQLITE_STATIC)) )
685 { 685 {
686 GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "ITERATE NAME HASH: `%8s'", GNUNET_NAMESTORE_short_h2s(&name_hase)); 686 GNUNET_log (GNUNET_ERROR_TYPE_ERROR,
687 "ITERATE NAME HASH: `%8s'",
688 GNUNET_NAMESTORE_short_h2s(&name_hase));
687 LOG_SQLITE (plugin, GNUNET_ERROR_TYPE_ERROR | GNUNET_ERROR_TYPE_BULK, 689 LOG_SQLITE (plugin, GNUNET_ERROR_TYPE_ERROR | GNUNET_ERROR_TYPE_BULK,
688 "sqlite3_bind_XXXX"); 690 "sqlite3_bind_XXXX");
689 if (SQLITE_OK != sqlite3_reset (stmt)) 691 if (SQLITE_OK != sqlite3_reset (stmt))