diff options
author | Martin Schanzenbach <schanzen@gnunet.org> | 2023-11-23 19:18:00 +0100 |
---|---|---|
committer | Martin Schanzenbach <schanzen@gnunet.org> | 2023-11-23 19:18:00 +0100 |
commit | d51ba6435b62772ccf2a20d13e99c164898bdc9d (patch) | |
tree | 349100514a23faf9a084fadd8dd55fca94bb8d7e | |
parent | 12ab12595f5021427c4d09623f0d7bb9aac21710 (diff) | |
download | gnunet-d51ba6435b62772ccf2a20d13e99c164898bdc9d.tar.gz gnunet-d51ba6435b62772ccf2a20d13e99c164898bdc9d.zip |
PEERSTORE: Major API overhault to fix a variety of race conditions.
-rw-r--r-- | src/include/gnunet_protocols.h | 6 | ||||
-rw-r--r-- | src/service/meson.build | 2 | ||||
-rw-r--r-- | src/service/peerstore/Makefile.am | 8 | ||||
-rw-r--r-- | src/service/peerstore/gnunet-service-peerstore.c | 133 | ||||
-rw-r--r-- | src/service/peerstore/meson.build | 55 | ||||
-rw-r--r-- | src/service/peerstore/peerstore.h | 33 | ||||
-rw-r--r-- | src/service/peerstore/peerstore_api.c | 419 | ||||
-rw-r--r-- | src/service/peerstore/peerstore_common.c | 17 | ||||
-rw-r--r-- | src/service/peerstore/peerstore_common.h | 4 | ||||
-rw-r--r-- | src/service/peerstore/perf_peerstore_store.c | 32 | ||||
-rw-r--r-- | src/service/peerstore/test_peerstore_api_iterate.c | 84 | ||||
-rw-r--r-- | src/service/peerstore/test_peerstore_api_store.c | 16 | ||||
-rw-r--r-- | src/service/peerstore/test_peerstore_api_sync.c | 252 | ||||
-rw-r--r-- | src/service/peerstore/test_peerstore_api_watch.c | 77 |
14 files changed, 549 insertions, 589 deletions
diff --git a/src/include/gnunet_protocols.h b/src/include/gnunet_protocols.h index 0daa37bed..a998344b9 100644 --- a/src/include/gnunet_protocols.h +++ b/src/include/gnunet_protocols.h | |||
@@ -2628,6 +2628,12 @@ extern "C" { | |||
2628 | */ | 2628 | */ |
2629 | #define GNUNET_MESSAGE_TYPE_PEERSTORE_WATCH_CANCEL 826 | 2629 | #define GNUNET_MESSAGE_TYPE_PEERSTORE_WATCH_CANCEL 826 |
2630 | 2630 | ||
2631 | /** | ||
2632 | * Store result message | ||
2633 | */ | ||
2634 | #define GNUNET_MESSAGE_TYPE_PEERSTORE_STORE_RESULT 827 | ||
2635 | |||
2636 | |||
2631 | /******************************************************************************* | 2637 | /******************************************************************************* |
2632 | * SOCIAL message types | 2638 | * SOCIAL message types |
2633 | ******************************************************************************/ | 2639 | ******************************************************************************/ |
diff --git a/src/service/meson.build b/src/service/meson.build index b5c4bc1ae..fcd3f7520 100644 --- a/src/service/meson.build +++ b/src/service/meson.build | |||
@@ -7,8 +7,8 @@ endif | |||
7 | subdir('util') | 7 | subdir('util') |
8 | subdir('statistics') | 8 | subdir('statistics') |
9 | subdir('arm') | 9 | subdir('arm') |
10 | subdir('peerstore') | ||
11 | subdir('testing') | 10 | subdir('testing') |
11 | subdir('peerstore') | ||
12 | subdir('nat') | 12 | subdir('nat') |
13 | subdir('nat-auto') | 13 | subdir('nat-auto') |
14 | subdir('transport') | 14 | subdir('transport') |
diff --git a/src/service/peerstore/Makefile.am b/src/service/peerstore/Makefile.am index 6ca8e7925..a12e8ff8b 100644 --- a/src/service/peerstore/Makefile.am +++ b/src/service/peerstore/Makefile.am | |||
@@ -44,7 +44,6 @@ check_PROGRAMS = \ | |||
44 | test_peerstore_api_store \ | 44 | test_peerstore_api_store \ |
45 | test_peerstore_api_iterate \ | 45 | test_peerstore_api_iterate \ |
46 | test_peerstore_api_watch \ | 46 | test_peerstore_api_watch \ |
47 | test_peerstore_api_sync \ | ||
48 | perf_peerstore_store | 47 | perf_peerstore_store |
49 | 48 | ||
50 | EXTRA_DIST = \ | 49 | EXTRA_DIST = \ |
@@ -76,13 +75,6 @@ test_peerstore_api_watch_LDADD = \ | |||
76 | $(top_builddir)/src/service/testing/libgnunettesting.la \ | 75 | $(top_builddir)/src/service/testing/libgnunettesting.la \ |
77 | $(top_builddir)/src/lib/util/libgnunetutil.la | 76 | $(top_builddir)/src/lib/util/libgnunetutil.la |
78 | 77 | ||
79 | test_peerstore_api_sync_SOURCES = \ | ||
80 | test_peerstore_api_sync.c | ||
81 | test_peerstore_api_sync_LDADD = \ | ||
82 | libgnunetpeerstore.la \ | ||
83 | $(top_builddir)/src/service/testing/libgnunettesting.la \ | ||
84 | $(top_builddir)/src/lib/util/libgnunetutil.la | ||
85 | |||
86 | perf_peerstore_store_SOURCES = \ | 78 | perf_peerstore_store_SOURCES = \ |
87 | perf_peerstore_store.c | 79 | perf_peerstore_store.c |
88 | perf_peerstore_store_LDADD = \ | 80 | perf_peerstore_store_LDADD = \ |
diff --git a/src/service/peerstore/gnunet-service-peerstore.c b/src/service/peerstore/gnunet-service-peerstore.c index 364900674..77523aa2e 100644 --- a/src/service/peerstore/gnunet-service-peerstore.c +++ b/src/service/peerstore/gnunet-service-peerstore.c | |||
@@ -100,6 +100,39 @@ do_shutdown () | |||
100 | } | 100 | } |
101 | 101 | ||
102 | 102 | ||
103 | struct IterationContext | ||
104 | { | ||
105 | /** | ||
106 | * The record that was stored. | ||
107 | */ | ||
108 | struct GNUNET_PEERSTORE_Record *record; | ||
109 | |||
110 | /** | ||
111 | * The request ID | ||
112 | */ | ||
113 | uint32_t rid; | ||
114 | |||
115 | }; | ||
116 | |||
117 | struct StoreRecordContext | ||
118 | { | ||
119 | /** | ||
120 | * The record that was stored. | ||
121 | */ | ||
122 | struct GNUNET_PEERSTORE_Record *record; | ||
123 | |||
124 | /** | ||
125 | * The request ID | ||
126 | */ | ||
127 | uint32_t rid; | ||
128 | |||
129 | /** | ||
130 | * The client | ||
131 | */ | ||
132 | struct GNUNET_SERVICE_Client *client; | ||
133 | }; | ||
134 | |||
135 | |||
103 | /** | 136 | /** |
104 | * Task run during shutdown. | 137 | * Task run during shutdown. |
105 | * | 138 | * |
@@ -245,31 +278,37 @@ record_iterator (void *cls, | |||
245 | const struct GNUNET_PEERSTORE_Record *record, | 278 | const struct GNUNET_PEERSTORE_Record *record, |
246 | const char *emsg) | 279 | const char *emsg) |
247 | { | 280 | { |
248 | struct GNUNET_PEERSTORE_Record *cls_record = cls; | 281 | struct IterationContext *ic = cls; |
249 | struct GNUNET_MQ_Envelope *env; | 282 | struct GNUNET_MQ_Envelope *env; |
250 | 283 | ||
251 | if (NULL == record) | 284 | if (NULL == record) |
252 | { | 285 | { |
253 | /* No more records */ | 286 | /* No more records */ |
254 | struct GNUNET_MessageHeader *endmsg; | 287 | struct PeerstoreResultMessage *endmsg; |
255 | 288 | ||
256 | env = GNUNET_MQ_msg (endmsg, GNUNET_MESSAGE_TYPE_PEERSTORE_ITERATE_END); | 289 | env = GNUNET_MQ_msg (endmsg, GNUNET_MESSAGE_TYPE_PEERSTORE_ITERATE_END); |
257 | GNUNET_MQ_send (GNUNET_SERVICE_client_get_mq (cls_record->client), env); | 290 | endmsg->rid = ic->rid; |
258 | if (NULL == emsg) | 291 | if (NULL == emsg) |
259 | { | 292 | { |
260 | GNUNET_SERVICE_client_continue (cls_record->client); | 293 | endmsg->result = htonl (GNUNET_OK); |
294 | GNUNET_MQ_send (GNUNET_SERVICE_client_get_mq (ic->record->client), env); | ||
295 | GNUNET_SERVICE_client_continue (ic->record->client); | ||
261 | } | 296 | } |
262 | else | 297 | else |
263 | { | 298 | { |
299 | endmsg->result = htonl (GNUNET_SYSERR); | ||
300 | GNUNET_MQ_send (GNUNET_SERVICE_client_get_mq (ic->record->client), env); | ||
264 | GNUNET_break (0); | 301 | GNUNET_break (0); |
265 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Failed to iterate: %s\n", emsg); | 302 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Failed to iterate: %s\n", emsg); |
266 | GNUNET_SERVICE_client_drop (cls_record->client); | 303 | GNUNET_SERVICE_client_drop (ic->record->client); |
267 | } | 304 | } |
268 | PEERSTORE_destroy_record (cls_record); | 305 | PEERSTORE_destroy_record (ic->record); |
306 | GNUNET_free (ic); | ||
269 | return; | 307 | return; |
270 | } | 308 | } |
271 | 309 | ||
272 | env = PEERSTORE_create_record_mq_envelope ( | 310 | env = PEERSTORE_create_record_mq_envelope ( |
311 | ic->rid, | ||
273 | record->sub_system, | 312 | record->sub_system, |
274 | &record->peer, | 313 | &record->peer, |
275 | record->key, | 314 | record->key, |
@@ -278,7 +317,7 @@ record_iterator (void *cls, | |||
278 | record->expiry, | 317 | record->expiry, |
279 | 0, | 318 | 0, |
280 | GNUNET_MESSAGE_TYPE_PEERSTORE_ITERATE_RECORD); | 319 | GNUNET_MESSAGE_TYPE_PEERSTORE_ITERATE_RECORD); |
281 | GNUNET_MQ_send (GNUNET_SERVICE_client_get_mq (cls_record->client), env); | 320 | GNUNET_MQ_send (GNUNET_SERVICE_client_get_mq (ic->record->client), env); |
282 | } | 321 | } |
283 | 322 | ||
284 | 323 | ||
@@ -300,6 +339,7 @@ watch_notifier_it (void *cls, const struct GNUNET_HashCode *key, void *value) | |||
300 | 339 | ||
301 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Found a watcher to update.\n"); | 340 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Found a watcher to update.\n"); |
302 | env = PEERSTORE_create_record_mq_envelope ( | 341 | env = PEERSTORE_create_record_mq_envelope ( |
342 | 0, | ||
303 | record->sub_system, | 343 | record->sub_system, |
304 | &record->peer, | 344 | &record->peer, |
305 | record->key, | 345 | record->key, |
@@ -415,27 +455,28 @@ check_iterate (void *cls, const struct StoreRecordMessage *srm) | |||
415 | static void | 455 | static void |
416 | handle_iterate (void *cls, const struct StoreRecordMessage *srm) | 456 | handle_iterate (void *cls, const struct StoreRecordMessage *srm) |
417 | { | 457 | { |
418 | struct GNUNET_SERVICE_Client *client = cls; | 458 | struct IterationContext *ic = GNUNET_new (struct IterationContext); |
419 | struct GNUNET_PEERSTORE_Record *record; | ||
420 | 459 | ||
421 | record = PEERSTORE_parse_record_message (srm); | 460 | ic->record = PEERSTORE_parse_record_message (srm); |
422 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | 461 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
423 | "Iterate request: ss `%s', peer `%s', key `%s'\n", | 462 | "Iterate request: ss `%s', peer `%s', key `%s'\n", |
424 | record->sub_system, | 463 | ic->record->sub_system, |
425 | GNUNET_i2s (&record->peer), | 464 | GNUNET_i2s (&ic->record->peer), |
426 | (NULL == record->key) ? "NULL" : record->key); | 465 | (NULL == ic->record->key) ? "NULL" : ic->record->key); |
427 | record->client = client; | 466 | ic->record->client = cls; |
467 | ic->rid = srm->rid; | ||
428 | if (GNUNET_OK != | 468 | if (GNUNET_OK != |
429 | db->iterate_records (db->cls, | 469 | db->iterate_records (db->cls, |
430 | record->sub_system, | 470 | ic->record->sub_system, |
431 | (ntohs (srm->peer_set)) ? &record->peer : NULL, | 471 | (ntohs (srm->peer_set)) ? &ic->record->peer : NULL, |
432 | record->key, | 472 | ic->record->key, |
433 | &record_iterator, | 473 | &record_iterator, |
434 | record)) | 474 | ic)) |
435 | { | 475 | { |
436 | GNUNET_break (0); | 476 | GNUNET_break (0); |
437 | GNUNET_SERVICE_client_drop (client); | 477 | GNUNET_SERVICE_client_drop (ic->record->client); |
438 | PEERSTORE_destroy_record (record); | 478 | PEERSTORE_destroy_record (ic->record); |
479 | GNUNET_free (ic); | ||
439 | } | 480 | } |
440 | } | 481 | } |
441 | 482 | ||
@@ -449,19 +490,28 @@ handle_iterate (void *cls, const struct StoreRecordMessage *srm) | |||
449 | static void | 490 | static void |
450 | store_record_continuation (void *cls, int success) | 491 | store_record_continuation (void *cls, int success) |
451 | { | 492 | { |
452 | struct GNUNET_PEERSTORE_Record *record = cls; | 493 | struct StoreRecordContext *src = cls; |
494 | struct PeerstoreResultMessage *msg; | ||
495 | struct GNUNET_MQ_Envelope *env; | ||
453 | 496 | ||
454 | if (GNUNET_OK == success) | 497 | if (GNUNET_OK == success) |
455 | { | 498 | { |
456 | watch_notifier (record); | 499 | |
457 | GNUNET_SERVICE_client_continue (record->client); | 500 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Found a watcher to update.\n"); |
501 | env = GNUNET_MQ_msg (msg, GNUNET_MESSAGE_TYPE_PEERSTORE_STORE_RESULT); | ||
502 | msg->rid = src->rid; | ||
503 | msg->result = htonl (success); | ||
504 | GNUNET_MQ_send (GNUNET_SERVICE_client_get_mq (src->client), env); | ||
505 | watch_notifier (src->record); | ||
506 | GNUNET_SERVICE_client_continue (src->client); | ||
458 | } | 507 | } |
459 | else | 508 | else |
460 | { | 509 | { |
461 | GNUNET_break (0); | 510 | GNUNET_break (0); |
462 | GNUNET_SERVICE_client_drop (record->client); | 511 | GNUNET_SERVICE_client_drop (src->record->client); |
463 | } | 512 | } |
464 | PEERSTORE_destroy_record (record); | 513 | PEERSTORE_destroy_record (src->record); |
514 | GNUNET_free (src); | ||
465 | } | 515 | } |
466 | 516 | ||
467 | 517 | ||
@@ -504,35 +554,38 @@ static void | |||
504 | handle_store (void *cls, const struct StoreRecordMessage *srm) | 554 | handle_store (void *cls, const struct StoreRecordMessage *srm) |
505 | { | 555 | { |
506 | struct GNUNET_SERVICE_Client *client = cls; | 556 | struct GNUNET_SERVICE_Client *client = cls; |
507 | struct GNUNET_PEERSTORE_Record *record; | 557 | struct StoreRecordContext *src = GNUNET_new (struct StoreRecordContext); |
508 | 558 | src->record = PEERSTORE_parse_record_message (srm); | |
509 | record = PEERSTORE_parse_record_message (srm); | ||
510 | GNUNET_log ( | 559 | GNUNET_log ( |
511 | GNUNET_ERROR_TYPE_DEBUG, | 560 | GNUNET_ERROR_TYPE_DEBUG, |
512 | "Received a store request. Sub system `%s' Peer `%s Key `%s' Options: %u.\n", | 561 | "Received a store request. Sub system `%s' Peer `%s Key `%s' Options: %u.\n", |
513 | record->sub_system, | 562 | src->record->sub_system, |
514 | GNUNET_i2s (&record->peer), | 563 | GNUNET_i2s (&src->record->peer), |
515 | record->key, | 564 | src->record->key, |
516 | (uint32_t) ntohl (srm->options)); | 565 | (uint32_t) ntohl (srm->options)); |
517 | record->client = client; | 566 | src->record->client = client; |
567 | src->rid = srm->rid; | ||
568 | src->client = client; | ||
518 | if (GNUNET_OK != db->store_record (db->cls, | 569 | if (GNUNET_OK != db->store_record (db->cls, |
519 | record->sub_system, | 570 | src->record->sub_system, |
520 | &record->peer, | 571 | &src->record->peer, |
521 | record->key, | 572 | src->record->key, |
522 | record->value, | 573 | src->record->value, |
523 | record->value_size, | 574 | src->record->value_size, |
524 | record->expiry, | 575 | src->record->expiry, |
525 | ntohl (srm->options), | 576 | ntohl (srm->options), |
526 | &store_record_continuation, | 577 | &store_record_continuation, |
527 | record)) | 578 | src)) |
528 | { | 579 | { |
529 | GNUNET_break (0); | 580 | GNUNET_break (0); |
530 | PEERSTORE_destroy_record (record); | 581 | PEERSTORE_destroy_record (src->record); |
582 | GNUNET_free (src); | ||
531 | GNUNET_SERVICE_client_drop (client); | 583 | GNUNET_SERVICE_client_drop (client); |
532 | return; | 584 | return; |
533 | } | 585 | } |
534 | } | 586 | } |
535 | 587 | ||
588 | |||
536 | static void | 589 | static void |
537 | store_hello_continuation (void *cls, int success) | 590 | store_hello_continuation (void *cls, int success) |
538 | { | 591 | { |
diff --git a/src/service/peerstore/meson.build b/src/service/peerstore/meson.build index db70b0b9e..2c6f7eba8 100644 --- a/src/service/peerstore/meson.build +++ b/src/service/peerstore/meson.build | |||
@@ -37,3 +37,58 @@ executable ('gnunet-service-peerstore', | |||
37 | install: true, | 37 | install: true, |
38 | install_dir: get_option('libdir') / 'gnunet' / 'libexec') | 38 | install_dir: get_option('libdir') / 'gnunet' / 'libexec') |
39 | 39 | ||
40 | testpeerstore_api_iterate = executable ('test_peerstore_api_iterate', | ||
41 | ['test_peerstore_api_iterate.c'], | ||
42 | dependencies: [ | ||
43 | libgnunetpeerstore_dep, | ||
44 | libgnunettesting_dep, | ||
45 | libgnunetutil_dep | ||
46 | ], | ||
47 | include_directories: [incdir, configuration_inc], | ||
48 | install: false) | ||
49 | |||
50 | testpeerstore_api_store = executable ('test_peerstore_api_store', | ||
51 | ['test_peerstore_api_store.c'], | ||
52 | dependencies: [ | ||
53 | libgnunetpeerstore_dep, | ||
54 | libgnunetutil_dep, | ||
55 | libgnunettesting_dep, | ||
56 | ], | ||
57 | include_directories: [incdir, configuration_inc], | ||
58 | install: false) | ||
59 | |||
60 | testpeerstore_api_watch = executable ('test_peerstore_api_watch', | ||
61 | ['test_peerstore_api_watch.c'], | ||
62 | dependencies: [ | ||
63 | libgnunetpeerstore_dep, | ||
64 | libgnunetutil_dep, | ||
65 | libgnunettesting_dep, | ||
66 | ], | ||
67 | include_directories: [incdir, configuration_inc], | ||
68 | install: false) | ||
69 | testpeerstore_api_perf = executable ('perf_peerstore_store', | ||
70 | ['perf_peerstore_store.c'], | ||
71 | dependencies: [ | ||
72 | libgnunetpeerstore_dep, | ||
73 | libgnunetutil_dep, | ||
74 | libgnunettesting_dep, | ||
75 | ], | ||
76 | include_directories: [incdir, configuration_inc], | ||
77 | install: false) | ||
78 | |||
79 | configure_file(input : 'test_peerstore_api_data.conf', | ||
80 | output : 'test_peerstore_api_data.conf', | ||
81 | copy: true) | ||
82 | |||
83 | test('test_peerstore_api_store', testpeerstore_api_store, | ||
84 | suite: 'peerstore', workdir: meson.current_build_dir()) | ||
85 | test('test_peerstore_api_watch', testpeerstore_api_watch, | ||
86 | suite: 'peerstore', workdir: meson.current_build_dir()) | ||
87 | test('test_peerstore_api_iterate', testpeerstore_api_iterate, | ||
88 | suite: 'peerstore', workdir: meson.current_build_dir()) | ||
89 | test('perf_peerstore_store', testpeerstore_api_perf, | ||
90 | suite: 'peerstore', workdir: meson.current_build_dir()) | ||
91 | |||
92 | |||
93 | |||
94 | |||
diff --git a/src/service/peerstore/peerstore.h b/src/service/peerstore/peerstore.h index 0dec03443..26c656f00 100644 --- a/src/service/peerstore/peerstore.h +++ b/src/service/peerstore/peerstore.h | |||
@@ -30,6 +30,7 @@ | |||
30 | 30 | ||
31 | 31 | ||
32 | GNUNET_NETWORK_STRUCT_BEGIN | 32 | GNUNET_NETWORK_STRUCT_BEGIN |
33 | |||
33 | /** | 34 | /** |
34 | * Message carrying a PEERSTORE record message | 35 | * Message carrying a PEERSTORE record message |
35 | */ | 36 | */ |
@@ -74,6 +75,11 @@ struct StoreRecordMessage | |||
74 | uint16_t value_size GNUNET_PACKED; | 75 | uint16_t value_size GNUNET_PACKED; |
75 | 76 | ||
76 | /** | 77 | /** |
78 | * Request id. | ||
79 | */ | ||
80 | uint32_t rid GNUNET_PACKED; | ||
81 | |||
82 | /** | ||
77 | * Options, needed only in case of a | 83 | * Options, needed only in case of a |
78 | * store operation | 84 | * store operation |
79 | */ | 85 | */ |
@@ -82,6 +88,28 @@ struct StoreRecordMessage | |||
82 | /* Followed by key and value */ | 88 | /* Followed by key and value */ |
83 | }; | 89 | }; |
84 | 90 | ||
91 | /** | ||
92 | * Message carrying a PEERSTORE result message | ||
93 | */ | ||
94 | struct PeerstoreResultMessage | ||
95 | { | ||
96 | /** | ||
97 | * GNUnet message header | ||
98 | */ | ||
99 | struct GNUNET_MessageHeader header; | ||
100 | |||
101 | /** | ||
102 | * Request id. | ||
103 | */ | ||
104 | uint32_t rid GNUNET_PACKED; | ||
105 | |||
106 | /** | ||
107 | * Options, needed only in case of a | ||
108 | * store operation | ||
109 | */ | ||
110 | uint32_t result GNUNET_PACKED; | ||
111 | |||
112 | }; | ||
85 | 113 | ||
86 | /** | 114 | /** |
87 | * Message carrying record key hash | 115 | * Message carrying record key hash |
@@ -94,14 +122,15 @@ struct StoreKeyHashMessage | |||
94 | struct GNUNET_MessageHeader header; | 122 | struct GNUNET_MessageHeader header; |
95 | 123 | ||
96 | /** | 124 | /** |
97 | * Always 0, for alignment. | 125 | * Request id. |
98 | */ | 126 | */ |
99 | uint32_t reserved GNUNET_PACKED; | 127 | uint32_t rid GNUNET_PACKED; |
100 | 128 | ||
101 | /** | 129 | /** |
102 | * Hash of a record key | 130 | * Hash of a record key |
103 | */ | 131 | */ |
104 | struct GNUNET_HashCode keyhash; | 132 | struct GNUNET_HashCode keyhash; |
133 | |||
105 | }; | 134 | }; |
106 | 135 | ||
107 | GNUNET_NETWORK_STRUCT_END | 136 | GNUNET_NETWORK_STRUCT_END |
diff --git a/src/service/peerstore/peerstore_api.c b/src/service/peerstore/peerstore_api.c index 3dec7e01b..394f64378 100644 --- a/src/service/peerstore/peerstore_api.c +++ b/src/service/peerstore/peerstore_api.c | |||
@@ -23,6 +23,7 @@ | |||
23 | * @author Omar Tarabai | 23 | * @author Omar Tarabai |
24 | * @author Christian Grothoff | 24 | * @author Christian Grothoff |
25 | */ | 25 | */ |
26 | #include "gnunet_common.h" | ||
26 | #include "platform.h" | 27 | #include "platform.h" |
27 | #include "gnunet_util_lib.h" | 28 | #include "gnunet_util_lib.h" |
28 | #include "gnunet_hello_uri_lib.h" | 29 | #include "gnunet_hello_uri_lib.h" |
@@ -86,6 +87,11 @@ struct GNUNET_PEERSTORE_Handle | |||
86 | */ | 87 | */ |
87 | struct GNUNET_TIME_Relative reconnect_delay; | 88 | struct GNUNET_TIME_Relative reconnect_delay; |
88 | 89 | ||
90 | /** | ||
91 | * | ||
92 | */ | ||
93 | uint32_t last_op_id; | ||
94 | |||
89 | }; | 95 | }; |
90 | 96 | ||
91 | /** | 97 | /** |
@@ -114,6 +120,11 @@ struct GNUNET_PEERSTORE_StoreContext | |||
114 | GNUNET_PEERSTORE_Continuation cont; | 120 | GNUNET_PEERSTORE_Continuation cont; |
115 | 121 | ||
116 | /** | 122 | /** |
123 | * Request ID | ||
124 | */ | ||
125 | uint32_t rid; | ||
126 | |||
127 | /** | ||
117 | * Closure for @e cont | 128 | * Closure for @e cont |
118 | */ | 129 | */ |
119 | void *cont_cls; | 130 | void *cont_cls; |
@@ -216,9 +227,10 @@ struct GNUNET_PEERSTORE_IterateContext | |||
216 | void *callback_cls; | 227 | void *callback_cls; |
217 | 228 | ||
218 | /** | 229 | /** |
219 | * #GNUNET_YES if we are currently processing records. | 230 | * Request ID |
220 | */ | 231 | */ |
221 | int iterating; | 232 | uint32_t rid; |
233 | |||
222 | }; | 234 | }; |
223 | 235 | ||
224 | /** | 236 | /** |
@@ -275,6 +287,12 @@ struct GNUNET_PEERSTORE_WatchContext | |||
275 | * The sub system requested the watch. | 287 | * The sub system requested the watch. |
276 | */ | 288 | */ |
277 | const char *sub_system; | 289 | const char *sub_system; |
290 | |||
291 | /** | ||
292 | * Request ID | ||
293 | */ | ||
294 | uint32_t rid; | ||
295 | |||
278 | }; | 296 | }; |
279 | 297 | ||
280 | /** | 298 | /** |
@@ -306,6 +324,12 @@ struct GNUNET_PEERSTORE_NotifyContext | |||
306 | * Is this request canceled. | 324 | * Is this request canceled. |
307 | */ | 325 | */ |
308 | unsigned int canceled; | 326 | unsigned int canceled; |
327 | |||
328 | /** | ||
329 | * Request ID | ||
330 | */ | ||
331 | uint32_t rid; | ||
332 | |||
309 | }; | 333 | }; |
310 | 334 | ||
311 | /******************************************************************************/ | 335 | /******************************************************************************/ |
@@ -320,6 +344,18 @@ struct GNUNET_PEERSTORE_NotifyContext | |||
320 | static void | 344 | static void |
321 | reconnect (void *cls); | 345 | reconnect (void *cls); |
322 | 346 | ||
347 | /** | ||
348 | * Get a fresh operation id to distinguish between namestore requests | ||
349 | * | ||
350 | * @param h the namestore handle | ||
351 | * @return next operation id to use | ||
352 | */ | ||
353 | static uint32_t | ||
354 | get_op_id (struct GNUNET_PEERSTORE_Handle *h) | ||
355 | { | ||
356 | return h->last_op_id++; | ||
357 | } | ||
358 | |||
323 | 359 | ||
324 | /** | 360 | /** |
325 | * Disconnect from the peerstore service. | 361 | * Disconnect from the peerstore service. |
@@ -329,25 +365,13 @@ reconnect (void *cls); | |||
329 | static void | 365 | static void |
330 | disconnect (struct GNUNET_PEERSTORE_Handle *h) | 366 | disconnect (struct GNUNET_PEERSTORE_Handle *h) |
331 | { | 367 | { |
332 | struct GNUNET_PEERSTORE_IterateContext *next; | 368 | if (NULL != h->watches) |
333 | |||
334 | for (struct GNUNET_PEERSTORE_IterateContext *ic = h->iterate_head; NULL != ic; | ||
335 | ic = next) | ||
336 | { | 369 | { |
337 | next = ic->next; | 370 | GNUNET_assert (0 == GNUNET_CONTAINER_multihashmap_size (h->watches)); |
338 | if (GNUNET_YES == ic->iterating) | 371 | GNUNET_CONTAINER_multihashmap_destroy (h->watches); |
339 | { | ||
340 | GNUNET_PEERSTORE_Processor icb; | ||
341 | void *icb_cls; | ||
342 | |||
343 | icb = ic->callback; | ||
344 | icb_cls = ic->callback_cls; | ||
345 | GNUNET_PEERSTORE_iterate_cancel (ic); | ||
346 | if (NULL != icb) | ||
347 | icb (icb_cls, NULL, "Iteration canceled due to reconnection"); | ||
348 | } | ||
349 | } | 372 | } |
350 | 373 | GNUNET_assert (NULL == h->iterate_head); | |
374 | GNUNET_assert (NULL == h->store_head); | ||
351 | if (NULL != h->mq) | 375 | if (NULL != h->mq) |
352 | { | 376 | { |
353 | GNUNET_MQ_destroy (h->mq); | 377 | GNUNET_MQ_destroy (h->mq); |
@@ -376,29 +400,6 @@ disconnect_and_schedule_reconnect (struct GNUNET_PEERSTORE_Handle *h) | |||
376 | } | 400 | } |
377 | 401 | ||
378 | 402 | ||
379 | /** | ||
380 | * Callback after MQ envelope is sent | ||
381 | * | ||
382 | * @param cls a `struct GNUNET_PEERSTORE_StoreContext *` | ||
383 | */ | ||
384 | static void | ||
385 | store_request_sent (void *cls) | ||
386 | { | ||
387 | struct GNUNET_PEERSTORE_StoreContext *sc = cls; | ||
388 | GNUNET_PEERSTORE_Continuation cont; | ||
389 | void *cont_cls; | ||
390 | |||
391 | if (NULL != sc) | ||
392 | { | ||
393 | cont = sc->cont; | ||
394 | cont_cls = sc->cont_cls; | ||
395 | GNUNET_PEERSTORE_store_cancel (sc); | ||
396 | if (NULL != cont) | ||
397 | cont (cont_cls, GNUNET_OK); | ||
398 | } | ||
399 | } | ||
400 | |||
401 | |||
402 | /******************************************************************************/ | 403 | /******************************************************************************/ |
403 | /******************* CONNECTION FUNCTIONS *********************/ | 404 | /******************* CONNECTION FUNCTIONS *********************/ |
404 | /******************************************************************************/ | 405 | /******************************************************************************/ |
@@ -437,30 +438,13 @@ rewatch_it (void *cls, const struct GNUNET_HashCode *key, void *value) | |||
437 | 438 | ||
438 | ev = GNUNET_MQ_msg (hm, GNUNET_MESSAGE_TYPE_PEERSTORE_WATCH); | 439 | ev = GNUNET_MQ_msg (hm, GNUNET_MESSAGE_TYPE_PEERSTORE_WATCH); |
439 | hm->keyhash = wc->keyhash; | 440 | hm->keyhash = wc->keyhash; |
441 | hm->rid = get_op_id (h); | ||
440 | GNUNET_MQ_send (h->mq, ev); | 442 | GNUNET_MQ_send (h->mq, ev); |
441 | return GNUNET_YES; | 443 | return GNUNET_YES; |
442 | } | 444 | } |
443 | 445 | ||
444 | 446 | ||
445 | /** | 447 | /** |
446 | * Iterator over watch requests to cancel them. | ||
447 | * | ||
448 | * @param cls unused | ||
449 | * @param key key to the watch request | ||
450 | * @param value watch context | ||
451 | * @return #GNUNET_YES to continue iteration | ||
452 | */ | ||
453 | static int | ||
454 | destroy_watch (void *cls, const struct GNUNET_HashCode *key, void *value) | ||
455 | { | ||
456 | struct GNUNET_PEERSTORE_WatchContext *wc = value; | ||
457 | |||
458 | GNUNET_PEERSTORE_watch_cancel (wc); | ||
459 | return GNUNET_YES; | ||
460 | } | ||
461 | |||
462 | |||
463 | /** | ||
464 | * Connect to the PEERSTORE service. | 448 | * Connect to the PEERSTORE service. |
465 | * | 449 | * |
466 | * @param cfg configuration to use | 450 | * @param cfg configuration to use |
@@ -493,26 +477,7 @@ GNUNET_PEERSTORE_connect (const struct GNUNET_CONFIGURATION_Handle *cfg) | |||
493 | void | 477 | void |
494 | GNUNET_PEERSTORE_disconnect (struct GNUNET_PEERSTORE_Handle *h) | 478 | GNUNET_PEERSTORE_disconnect (struct GNUNET_PEERSTORE_Handle *h) |
495 | { | 479 | { |
496 | struct GNUNET_PEERSTORE_IterateContext *ic; | 480 | LOG (GNUNET_ERROR_TYPE_DEBUG, "Disconnect initiated from client.\n"); |
497 | struct GNUNET_PEERSTORE_StoreContext *sc; | ||
498 | |||
499 | LOG (GNUNET_ERROR_TYPE_DEBUG, "Disconnecting.\n"); | ||
500 | if (NULL != h->watches) | ||
501 | { | ||
502 | GNUNET_CONTAINER_multihashmap_iterate (h->watches, &destroy_watch, NULL); | ||
503 | GNUNET_CONTAINER_multihashmap_destroy (h->watches); | ||
504 | h->watches = NULL; | ||
505 | } | ||
506 | while (NULL != (ic = h->iterate_head)) | ||
507 | { | ||
508 | GNUNET_break (0); | ||
509 | GNUNET_PEERSTORE_iterate_cancel (ic); | ||
510 | } | ||
511 | while (NULL != (sc = h->store_head)) | ||
512 | { | ||
513 | GNUNET_break (0); | ||
514 | GNUNET_PEERSTORE_store_cancel (sc); | ||
515 | } | ||
516 | disconnect (h); | 481 | disconnect (h); |
517 | } | 482 | } |
518 | 483 | ||
@@ -530,17 +495,17 @@ GNUNET_PEERSTORE_disconnect (struct GNUNET_PEERSTORE_Handle *h) | |||
530 | void | 495 | void |
531 | GNUNET_PEERSTORE_store_cancel (struct GNUNET_PEERSTORE_StoreContext *sc) | 496 | GNUNET_PEERSTORE_store_cancel (struct GNUNET_PEERSTORE_StoreContext *sc) |
532 | { | 497 | { |
533 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | 498 | LOG (GNUNET_ERROR_TYPE_DEBUG, |
534 | "store cancel with sc %p \n", | 499 | "store cancel with sc %p \n", |
535 | sc); | 500 | sc); |
536 | GNUNET_CONTAINER_DLL_remove (sc->h->store_head, sc->h->store_tail, sc); | 501 | GNUNET_CONTAINER_DLL_remove (sc->h->store_head, sc->h->store_tail, sc); |
537 | GNUNET_free (sc->sub_system); | 502 | GNUNET_free (sc->sub_system); |
538 | GNUNET_free (sc->value); | 503 | GNUNET_free (sc->value); |
539 | GNUNET_free (sc->key); | 504 | GNUNET_free (sc->key); |
540 | GNUNET_free (sc); | 505 | GNUNET_free (sc); |
541 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | 506 | LOG (GNUNET_ERROR_TYPE_DEBUG, |
542 | "store cancel with sc %p is null\n", | 507 | "store cancel with sc %p is null\n", |
543 | sc); | 508 | sc); |
544 | } | 509 | } |
545 | 510 | ||
546 | 511 | ||
@@ -581,17 +546,8 @@ GNUNET_PEERSTORE_store (struct GNUNET_PEERSTORE_Handle *h, | |||
581 | sub_system, | 546 | sub_system, |
582 | GNUNET_i2s (peer), | 547 | GNUNET_i2s (peer), |
583 | key); | 548 | key); |
584 | ev = | ||
585 | PEERSTORE_create_record_mq_envelope (sub_system, | ||
586 | peer, | ||
587 | key, | ||
588 | value, | ||
589 | size, | ||
590 | expiry, | ||
591 | options, | ||
592 | GNUNET_MESSAGE_TYPE_PEERSTORE_STORE); | ||
593 | sc = GNUNET_new (struct GNUNET_PEERSTORE_StoreContext); | 549 | sc = GNUNET_new (struct GNUNET_PEERSTORE_StoreContext); |
594 | 550 | sc->rid = get_op_id (h); | |
595 | sc->sub_system = GNUNET_strdup (sub_system); | 551 | sc->sub_system = GNUNET_strdup (sub_system); |
596 | sc->peer = *peer; | 552 | sc->peer = *peer; |
597 | sc->key = GNUNET_strdup (key); | 553 | sc->key = GNUNET_strdup (key); |
@@ -602,14 +558,54 @@ GNUNET_PEERSTORE_store (struct GNUNET_PEERSTORE_Handle *h, | |||
602 | sc->cont = cont; | 558 | sc->cont = cont; |
603 | sc->cont_cls = cont_cls; | 559 | sc->cont_cls = cont_cls; |
604 | sc->h = h; | 560 | sc->h = h; |
561 | ev = | ||
562 | PEERSTORE_create_record_mq_envelope (sc->rid, | ||
563 | sub_system, | ||
564 | peer, | ||
565 | key, | ||
566 | value, | ||
567 | size, | ||
568 | expiry, | ||
569 | options, | ||
570 | GNUNET_MESSAGE_TYPE_PEERSTORE_STORE); | ||
605 | 571 | ||
606 | GNUNET_CONTAINER_DLL_insert_tail (h->store_head, h->store_tail, sc); | 572 | GNUNET_CONTAINER_DLL_insert_tail (h->store_head, h->store_tail, sc); |
607 | GNUNET_MQ_notify_sent (ev, &store_request_sent, sc); | ||
608 | GNUNET_MQ_send (h->mq, ev); | 573 | GNUNET_MQ_send (h->mq, ev); |
609 | return sc; | 574 | return sc; |
610 | } | 575 | } |
611 | 576 | ||
612 | 577 | ||
578 | /** | ||
579 | * When a response for store request is received | ||
580 | * | ||
581 | * @param cls a `struct GNUNET_PEERSTORE_Handle *` | ||
582 | * @param msg message received | ||
583 | */ | ||
584 | static void | ||
585 | handle_store_result (void *cls, const struct PeerstoreResultMessage *msg) | ||
586 | { | ||
587 | struct GNUNET_PEERSTORE_Handle *h = cls; | ||
588 | struct GNUNET_PEERSTORE_StoreContext *sc = h->store_head; | ||
589 | |||
590 | LOG (GNUNET_ERROR_TYPE_DEBUG, "Got PeerstoreResultMessage\n"); | ||
591 | for (sc = h->store_head; NULL != sc; sc = sc->next) | ||
592 | { | ||
593 | LOG (GNUNET_ERROR_TYPE_DEBUG, "Trying %u ?= %u\n", sc->rid, msg->rid); | ||
594 | if (sc->rid == msg->rid) | ||
595 | break; | ||
596 | } | ||
597 | if (NULL == sc) | ||
598 | { | ||
599 | LOG (GNUNET_ERROR_TYPE_WARNING, | ||
600 | _("Unexpected store response.\n")); | ||
601 | return; | ||
602 | } | ||
603 | if (NULL != sc->cont) | ||
604 | sc->cont (sc->cont_cls, ntohl (msg->result)); | ||
605 | GNUNET_CONTAINER_DLL_remove (h->store_head, h->store_tail, sc); | ||
606 | } | ||
607 | |||
608 | |||
613 | /******************************************************************************/ | 609 | /******************************************************************************/ |
614 | /******************* ITERATE FUNCTIONS *********************/ | 610 | /******************* ITERATE FUNCTIONS *********************/ |
615 | /******************************************************************************/ | 611 | /******************************************************************************/ |
@@ -622,29 +618,24 @@ GNUNET_PEERSTORE_store (struct GNUNET_PEERSTORE_Handle *h, | |||
622 | * @param msg message received | 618 | * @param msg message received |
623 | */ | 619 | */ |
624 | static void | 620 | static void |
625 | handle_iterate_end (void *cls, const struct GNUNET_MessageHeader *msg) | 621 | handle_iterate_end (void *cls, const struct PeerstoreResultMessage *msg) |
626 | { | 622 | { |
627 | struct GNUNET_PEERSTORE_Handle *h = cls; | 623 | struct GNUNET_PEERSTORE_Handle *h = cls; |
628 | struct GNUNET_PEERSTORE_IterateContext *ic; | 624 | struct GNUNET_PEERSTORE_IterateContext *ic = h->iterate_head; |
629 | GNUNET_PEERSTORE_Processor callback; | ||
630 | void *callback_cls; | ||
631 | 625 | ||
632 | ic = h->iterate_head; | 626 | for (ic = h->iterate_head; NULL != ic; ic = ic->next) |
627 | if (ic->rid == msg->rid) | ||
628 | break; | ||
633 | if (NULL == ic) | 629 | if (NULL == ic) |
634 | { | 630 | { |
635 | LOG (GNUNET_ERROR_TYPE_ERROR, | 631 | LOG (GNUNET_ERROR_TYPE_WARNING, |
636 | _ ("Unexpected iteration response, this should not happen.\n")); | 632 | _ ("Unexpected iteration response.\n")); |
637 | disconnect_and_schedule_reconnect (h); | ||
638 | return; | 633 | return; |
639 | } | 634 | } |
640 | callback = ic->callback; | 635 | if (NULL != ic->callback) |
641 | callback_cls = ic->callback_cls; | 636 | ic->callback (ic->callback_cls, NULL, NULL); |
642 | ic->iterating = GNUNET_NO; | 637 | LOG (GNUNET_ERROR_TYPE_DEBUG, "Cleaning up iteration with rid %u\n", ic->rid); |
643 | GNUNET_PEERSTORE_iterate_cancel (ic); | 638 | GNUNET_CONTAINER_DLL_remove (h->iterate_head, h->iterate_tail, ic); |
644 | /* NOTE: set this here and not after callback because callback may free h */ | ||
645 | h->reconnect_delay = GNUNET_TIME_UNIT_ZERO; | ||
646 | if (NULL != callback) | ||
647 | callback (callback_cls, NULL, NULL); | ||
648 | } | 639 | } |
649 | 640 | ||
650 | 641 | ||
@@ -674,11 +665,12 @@ handle_iterate_result (void *cls, const struct StoreRecordMessage *msg) | |||
674 | { | 665 | { |
675 | struct GNUNET_PEERSTORE_Handle *h = cls; | 666 | struct GNUNET_PEERSTORE_Handle *h = cls; |
676 | struct GNUNET_PEERSTORE_IterateContext *ic; | 667 | struct GNUNET_PEERSTORE_IterateContext *ic; |
677 | GNUNET_PEERSTORE_Processor callback; | ||
678 | void *callback_cls; | ||
679 | struct GNUNET_PEERSTORE_Record *record; | 668 | struct GNUNET_PEERSTORE_Record *record; |
680 | 669 | ||
681 | ic = h->iterate_head; | 670 | LOG (GNUNET_ERROR_TYPE_DEBUG, "Received StoreRecordMessage\n"); |
671 | for (ic = h->iterate_head; NULL != ic; ic = ic->next) | ||
672 | if (ic->rid == msg->rid) | ||
673 | break; | ||
682 | if (NULL == ic) | 674 | if (NULL == ic) |
683 | { | 675 | { |
684 | LOG (GNUNET_ERROR_TYPE_ERROR, | 676 | LOG (GNUNET_ERROR_TYPE_ERROR, |
@@ -686,21 +678,18 @@ handle_iterate_result (void *cls, const struct StoreRecordMessage *msg) | |||
686 | disconnect_and_schedule_reconnect (h); | 678 | disconnect_and_schedule_reconnect (h); |
687 | return; | 679 | return; |
688 | } | 680 | } |
689 | ic->iterating = GNUNET_YES; | 681 | if (NULL == ic->callback) |
690 | callback = ic->callback; | ||
691 | callback_cls = ic->callback_cls; | ||
692 | if (NULL == callback) | ||
693 | return; | 682 | return; |
694 | record = PEERSTORE_parse_record_message (msg); | 683 | record = PEERSTORE_parse_record_message (msg); |
695 | if (NULL == record) | 684 | if (NULL == record) |
696 | { | 685 | { |
697 | callback (callback_cls, | 686 | ic->callback (ic->callback_cls, |
698 | NULL, | 687 | NULL, |
699 | _ ("Received a malformed response from service.")); | 688 | _ ("Received a malformed response from service.")); |
700 | } | 689 | } |
701 | else | 690 | else |
702 | { | 691 | { |
703 | callback (callback_cls, record, NULL); | 692 | ic->callback (ic->callback_cls, record, NULL); |
704 | PEERSTORE_destroy_record (record); | 693 | PEERSTORE_destroy_record (record); |
705 | } | 694 | } |
706 | } | 695 | } |
@@ -715,11 +704,6 @@ handle_iterate_result (void *cls, const struct StoreRecordMessage *msg) | |||
715 | void | 704 | void |
716 | GNUNET_PEERSTORE_iterate_cancel (struct GNUNET_PEERSTORE_IterateContext *ic) | 705 | GNUNET_PEERSTORE_iterate_cancel (struct GNUNET_PEERSTORE_IterateContext *ic) |
717 | { | 706 | { |
718 | if (GNUNET_YES == ic->iterating) | ||
719 | { | ||
720 | if (NULL != ic->callback) | ||
721 | ic->callback (ic->callback_cls, NULL, "Iteration canceled due to reconnection"); | ||
722 | } | ||
723 | GNUNET_CONTAINER_DLL_remove (ic->h->iterate_head, ic->h->iterate_tail, ic); | 707 | GNUNET_CONTAINER_DLL_remove (ic->h->iterate_head, ic->h->iterate_tail, ic); |
724 | GNUNET_free (ic->sub_system); | 708 | GNUNET_free (ic->sub_system); |
725 | GNUNET_free (ic->key); | 709 | GNUNET_free (ic->key); |
@@ -738,8 +722,11 @@ GNUNET_PEERSTORE_iterate (struct GNUNET_PEERSTORE_Handle *h, | |||
738 | struct GNUNET_MQ_Envelope *ev; | 722 | struct GNUNET_MQ_Envelope *ev; |
739 | struct GNUNET_PEERSTORE_IterateContext *ic; | 723 | struct GNUNET_PEERSTORE_IterateContext *ic; |
740 | 724 | ||
725 | ic = GNUNET_new (struct GNUNET_PEERSTORE_IterateContext); | ||
726 | ic->rid = get_op_id (h); | ||
741 | ev = | 727 | ev = |
742 | PEERSTORE_create_record_mq_envelope (sub_system, | 728 | PEERSTORE_create_record_mq_envelope (ic->rid, |
729 | sub_system, | ||
743 | peer, | 730 | peer, |
744 | key, | 731 | key, |
745 | NULL, | 732 | NULL, |
@@ -747,7 +734,6 @@ GNUNET_PEERSTORE_iterate (struct GNUNET_PEERSTORE_Handle *h, | |||
747 | GNUNET_TIME_UNIT_FOREVER_ABS, | 734 | GNUNET_TIME_UNIT_FOREVER_ABS, |
748 | 0, | 735 | 0, |
749 | GNUNET_MESSAGE_TYPE_PEERSTORE_ITERATE); | 736 | GNUNET_MESSAGE_TYPE_PEERSTORE_ITERATE); |
750 | ic = GNUNET_new (struct GNUNET_PEERSTORE_IterateContext); | ||
751 | ic->callback = callback; | 737 | ic->callback = callback; |
752 | ic->callback_cls = callback_cls; | 738 | ic->callback_cls = callback_cls; |
753 | ic->h = h; | 739 | ic->h = h; |
@@ -831,10 +817,14 @@ static void | |||
831 | reconnect (void *cls) | 817 | reconnect (void *cls) |
832 | { | 818 | { |
833 | struct GNUNET_PEERSTORE_Handle *h = cls; | 819 | struct GNUNET_PEERSTORE_Handle *h = cls; |
834 | struct GNUNET_MQ_MessageHandler mq_handlers[] = | 820 | struct GNUNET_MQ_MessageHandler mq_handlers[] = { |
835 | { GNUNET_MQ_hd_fixed_size (iterate_end, | 821 | GNUNET_MQ_hd_fixed_size (iterate_end, |
836 | GNUNET_MESSAGE_TYPE_PEERSTORE_ITERATE_END, | 822 | GNUNET_MESSAGE_TYPE_PEERSTORE_ITERATE_END, |
837 | struct GNUNET_MessageHeader, | 823 | struct PeerstoreResultMessage, |
824 | h), | ||
825 | GNUNET_MQ_hd_fixed_size (store_result, | ||
826 | GNUNET_MESSAGE_TYPE_PEERSTORE_STORE_RESULT, | ||
827 | struct PeerstoreResultMessage, | ||
838 | h), | 828 | h), |
839 | GNUNET_MQ_hd_var_size (iterate_result, | 829 | GNUNET_MQ_hd_var_size (iterate_result, |
840 | GNUNET_MESSAGE_TYPE_PEERSTORE_ITERATE_RECORD, | 830 | GNUNET_MESSAGE_TYPE_PEERSTORE_ITERATE_RECORD, |
@@ -844,7 +834,8 @@ reconnect (void *cls) | |||
844 | GNUNET_MESSAGE_TYPE_PEERSTORE_WATCH_RECORD, | 834 | GNUNET_MESSAGE_TYPE_PEERSTORE_WATCH_RECORD, |
845 | struct StoreRecordMessage, | 835 | struct StoreRecordMessage, |
846 | h), | 836 | h), |
847 | GNUNET_MQ_handler_end () }; | 837 | GNUNET_MQ_handler_end () |
838 | }; | ||
848 | struct GNUNET_MQ_Envelope *ev; | 839 | struct GNUNET_MQ_Envelope *ev; |
849 | 840 | ||
850 | h->reconnect_task = NULL; | 841 | h->reconnect_task = NULL; |
@@ -868,8 +859,10 @@ reconnect (void *cls) | |||
868 | for (struct GNUNET_PEERSTORE_IterateContext *ic = h->iterate_head; NULL != ic; | 859 | for (struct GNUNET_PEERSTORE_IterateContext *ic = h->iterate_head; NULL != ic; |
869 | ic = ic->next) | 860 | ic = ic->next) |
870 | { | 861 | { |
862 | ic->rid = get_op_id(h); | ||
871 | ev = | 863 | ev = |
872 | PEERSTORE_create_record_mq_envelope (ic->sub_system, | 864 | PEERSTORE_create_record_mq_envelope (ic->rid, |
865 | ic->sub_system, | ||
873 | &ic->peer, | 866 | &ic->peer, |
874 | ic->key, | 867 | ic->key, |
875 | NULL, | 868 | NULL, |
@@ -882,8 +875,10 @@ reconnect (void *cls) | |||
882 | for (struct GNUNET_PEERSTORE_StoreContext *sc = h->store_head; NULL != sc; | 875 | for (struct GNUNET_PEERSTORE_StoreContext *sc = h->store_head; NULL != sc; |
883 | sc = sc->next) | 876 | sc = sc->next) |
884 | { | 877 | { |
878 | sc->rid = get_op_id(h); | ||
885 | ev = | 879 | ev = |
886 | PEERSTORE_create_record_mq_envelope (sc->sub_system, | 880 | PEERSTORE_create_record_mq_envelope (sc->rid, |
881 | sc->sub_system, | ||
887 | &sc->peer, | 882 | &sc->peer, |
888 | sc->key, | 883 | sc->key, |
889 | sc->value, | 884 | sc->value, |
@@ -891,7 +886,6 @@ reconnect (void *cls) | |||
891 | sc->expiry, | 886 | sc->expiry, |
892 | sc->options, | 887 | sc->options, |
893 | GNUNET_MESSAGE_TYPE_PEERSTORE_STORE); | 888 | GNUNET_MESSAGE_TYPE_PEERSTORE_STORE); |
894 | GNUNET_MQ_notify_sent (ev, &store_request_sent, sc); | ||
895 | GNUNET_MQ_send (h->mq, ev); | 889 | GNUNET_MQ_send (h->mq, ev); |
896 | } | 890 | } |
897 | } | 891 | } |
@@ -909,7 +903,7 @@ GNUNET_PEERSTORE_watch_cancel (struct GNUNET_PEERSTORE_WatchContext *wc) | |||
909 | struct GNUNET_MQ_Envelope *ev; | 903 | struct GNUNET_MQ_Envelope *ev; |
910 | struct StoreKeyHashMessage *hm; | 904 | struct StoreKeyHashMessage *hm; |
911 | 905 | ||
912 | LOG (GNUNET_ERROR_TYPE_DEBUG, "Canceling watch.\n"); | 906 | LOG (GNUNET_ERROR_TYPE_DEBUG, "Cancelling watch.\n"); |
913 | if (NULL != wc->ic) | 907 | if (NULL != wc->ic) |
914 | { | 908 | { |
915 | GNUNET_PEERSTORE_iterate_cancel (wc->ic); | 909 | GNUNET_PEERSTORE_iterate_cancel (wc->ic); |
@@ -919,6 +913,7 @@ GNUNET_PEERSTORE_watch_cancel (struct GNUNET_PEERSTORE_WatchContext *wc) | |||
919 | 913 | ||
920 | ev = GNUNET_MQ_msg (hm, GNUNET_MESSAGE_TYPE_PEERSTORE_WATCH_CANCEL); | 914 | ev = GNUNET_MQ_msg (hm, GNUNET_MESSAGE_TYPE_PEERSTORE_WATCH_CANCEL); |
921 | hm->keyhash = wc->keyhash; | 915 | hm->keyhash = wc->keyhash; |
916 | hm->rid = get_op_id (h); | ||
922 | GNUNET_MQ_send (h->mq, ev); | 917 | GNUNET_MQ_send (h->mq, ev); |
923 | GNUNET_assert ( | 918 | GNUNET_assert ( |
924 | GNUNET_YES == | 919 | GNUNET_YES == |
@@ -935,53 +930,55 @@ watch_iterate (void *cls, | |||
935 | struct GNUNET_PEERSTORE_WatchContext *wc = cls; | 930 | struct GNUNET_PEERSTORE_WatchContext *wc = cls; |
936 | struct GNUNET_PEERSTORE_Handle *h = wc->h; | 931 | struct GNUNET_PEERSTORE_Handle *h = wc->h; |
937 | struct StoreKeyHashMessage *hm; | 932 | struct StoreKeyHashMessage *hm; |
933 | struct GNUNET_MQ_Envelope *ev; | ||
934 | const struct GNUNET_PeerIdentity *peer; | ||
938 | 935 | ||
939 | if (NULL != emsg) | 936 | if (NULL != emsg) |
940 | { | 937 | { |
941 | GNUNET_log (GNUNET_ERROR_TYPE_WARNING, | 938 | LOG (GNUNET_ERROR_TYPE_WARNING, |
942 | "Got failure from PEERSTORE: %s\n", | 939 | "Got failure from PEERSTORE: %s\n", |
943 | emsg); | 940 | emsg); |
944 | wc->callback (wc->callback_cls, NULL, emsg); | 941 | wc->callback (wc->callback_cls, NULL, emsg); |
945 | return; | 942 | return; |
946 | } | 943 | } |
947 | if (NULL == record) | 944 | if ((NULL != record) && |
945 | (NULL != wc->callback)) | ||
948 | { | 946 | { |
949 | struct GNUNET_MQ_Envelope *ev; | 947 | wc->callback (wc->callback_cls, record, NULL); |
950 | const struct GNUNET_PeerIdentity *peer; | ||
951 | |||
952 | if (NULL == wc->peer) | ||
953 | peer = GNUNET_new (struct GNUNET_PeerIdentity); | ||
954 | else | ||
955 | peer = wc->peer; | ||
956 | ev = GNUNET_MQ_msg (hm, GNUNET_MESSAGE_TYPE_PEERSTORE_WATCH); | ||
957 | PEERSTORE_hash_key (wc->sub_system, peer, wc->key, &hm->keyhash); | ||
958 | LOG (GNUNET_ERROR_TYPE_DEBUG, | ||
959 | "Hash key we watch for %s\n", | ||
960 | GNUNET_h2s_full (&hm->keyhash)); | ||
961 | wc->keyhash = hm->keyhash; | ||
962 | if (NULL == h->watches) | ||
963 | h->watches = GNUNET_CONTAINER_multihashmap_create (5, GNUNET_NO); | ||
964 | GNUNET_assert (GNUNET_OK == GNUNET_CONTAINER_multihashmap_put ( | ||
965 | h->watches, | ||
966 | &wc->keyhash, | ||
967 | wc, | ||
968 | GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE)); | ||
969 | LOG (GNUNET_ERROR_TYPE_DEBUG, | ||
970 | "Sending a watch request for subsystem `%s', peer `%s', key `%s'.\n", | ||
971 | wc->sub_system, | ||
972 | GNUNET_i2s (peer), | ||
973 | wc->key); | ||
974 | GNUNET_MQ_send (h->mq, ev); | ||
975 | wc->ic = NULL; | ||
976 | if (NULL != wc->callback) | ||
977 | wc->callback (wc->callback_cls, record, NULL); | ||
978 | if (NULL == wc->peer) | ||
979 | GNUNET_free_nz ((void *) peer); | ||
980 | return; | 948 | return; |
981 | } | 949 | } |
982 | 950 | ||
951 | if (NULL == wc->peer) | ||
952 | peer = GNUNET_new (struct GNUNET_PeerIdentity); | ||
953 | else | ||
954 | peer = wc->peer; | ||
955 | ev = GNUNET_MQ_msg (hm, GNUNET_MESSAGE_TYPE_PEERSTORE_WATCH); | ||
956 | PEERSTORE_hash_key (wc->sub_system, peer, wc->key, &hm->keyhash); | ||
957 | hm->rid = get_op_id (h); | ||
958 | LOG (GNUNET_ERROR_TYPE_DEBUG, | ||
959 | "Hash key we watch for %s\n", | ||
960 | GNUNET_h2s_full (&hm->keyhash)); | ||
961 | wc->keyhash = hm->keyhash; | ||
962 | if (NULL == h->watches) | ||
963 | h->watches = GNUNET_CONTAINER_multihashmap_create (5, GNUNET_NO); | ||
964 | GNUNET_assert (GNUNET_OK == GNUNET_CONTAINER_multihashmap_put ( | ||
965 | h->watches, | ||
966 | &wc->keyhash, | ||
967 | wc, | ||
968 | GNUNET_CONTAINER_MULTIHASHMAPOPTION_MULTIPLE)); | ||
969 | LOG (GNUNET_ERROR_TYPE_DEBUG, | ||
970 | "Sending a watch request for subsystem `%s', peer `%s', key `%s'.\n", | ||
971 | wc->sub_system, | ||
972 | GNUNET_i2s (peer), | ||
973 | wc->key); | ||
974 | GNUNET_MQ_send (h->mq, ev); | ||
975 | wc->ic = NULL; | ||
983 | if (NULL != wc->callback) | 976 | if (NULL != wc->callback) |
984 | wc->callback (wc->callback_cls, record, NULL); | 977 | wc->callback (wc->callback_cls, record, NULL); |
978 | if (NULL == wc->peer) | ||
979 | GNUNET_free_nz ((void *) peer); | ||
980 | return; | ||
981 | |||
985 | } | 982 | } |
986 | 983 | ||
987 | 984 | ||
@@ -1040,32 +1037,32 @@ hello_updated (void *cls, | |||
1040 | struct GNUNET_PEERSTORE_NotifyContext *nc = cls; | 1037 | struct GNUNET_PEERSTORE_NotifyContext *nc = cls; |
1041 | const struct GNUNET_MessageHeader *hello; | 1038 | const struct GNUNET_MessageHeader *hello; |
1042 | 1039 | ||
1043 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | 1040 | LOG (GNUNET_ERROR_TYPE_DEBUG, |
1044 | "hello_updated\n"); | 1041 | "hello_updated\n"); |
1045 | if (NULL != emsg) | 1042 | if (NULL != emsg) |
1046 | { | 1043 | { |
1047 | GNUNET_log (GNUNET_ERROR_TYPE_WARNING, | 1044 | LOG (GNUNET_ERROR_TYPE_WARNING, |
1048 | "Got failure from PEERSTORE: %s\n", | 1045 | "Got failure from PEERSTORE: %s\n", |
1049 | emsg); | 1046 | emsg); |
1050 | nc->callback (nc->callback_cls, NULL, NULL, emsg); | 1047 | nc->callback (nc->callback_cls, NULL, NULL, emsg); |
1051 | return; | 1048 | return; |
1052 | } | 1049 | } |
1053 | if (NULL == record) | 1050 | if (NULL == record) |
1054 | return; | 1051 | return; |
1055 | hello = record->value; | 1052 | hello = record->value; |
1056 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | 1053 | LOG (GNUNET_ERROR_TYPE_DEBUG, |
1057 | "hello_updated with expired %s and size %u for peer %s\n", | 1054 | "hello_updated with expired %s and size %u for peer %s\n", |
1058 | GNUNET_STRINGS_absolute_time_to_string ( | 1055 | GNUNET_STRINGS_absolute_time_to_string ( |
1059 | GNUNET_HELLO_builder_get_expiration_time (hello)), | 1056 | GNUNET_HELLO_builder_get_expiration_time (hello)), |
1060 | ntohs (hello->size), | 1057 | ntohs (hello->size), |
1061 | GNUNET_i2s (&record->peer)); | 1058 | GNUNET_i2s (&record->peer)); |
1062 | if ((0 == record->value_size)) | 1059 | if ((0 == record->value_size)) |
1063 | { | 1060 | { |
1064 | GNUNET_break (0); | 1061 | GNUNET_break (0); |
1065 | return; | 1062 | return; |
1066 | } | 1063 | } |
1067 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | 1064 | LOG (GNUNET_ERROR_TYPE_DEBUG, |
1068 | "hello_updated call callback\n"); | 1065 | "hello_updated call callback\n"); |
1069 | nc->callback (nc->callback_cls, &record->peer, hello, NULL); | 1066 | nc->callback (nc->callback_cls, &record->peer, hello, NULL); |
1070 | } | 1067 | } |
1071 | 1068 | ||
@@ -1119,13 +1116,13 @@ merge_success (void *cls, int success) | |||
1119 | 1116 | ||
1120 | if (GNUNET_NO == GNUNET_CONTAINER_multipeermap_remove (huc->store_context_map, | 1117 | if (GNUNET_NO == GNUNET_CONTAINER_multipeermap_remove (huc->store_context_map, |
1121 | huc->pid, shu_cls->sc)) | 1118 | huc->pid, shu_cls->sc)) |
1122 | GNUNET_log (GNUNET_ERROR_TYPE_WARNING, | 1119 | LOG (GNUNET_ERROR_TYPE_WARNING, |
1123 | "There was no store context to be removed after storing hello for peer %s\n", | 1120 | "There was no store context to be removed after storing hello for peer %s\n", |
1124 | GNUNET_i2s (huc->pid)); | 1121 | GNUNET_i2s (huc->pid)); |
1125 | if (GNUNET_OK != success) | 1122 | if (GNUNET_OK != success) |
1126 | { | 1123 | { |
1127 | GNUNET_log (GNUNET_ERROR_TYPE_WARNING, | 1124 | LOG (GNUNET_ERROR_TYPE_WARNING, |
1128 | "Storing hello uri failed\n"); | 1125 | "Storing hello uri failed\n"); |
1129 | huc->cont (huc->cont_cls, success); | 1126 | huc->cont (huc->cont_cls, success); |
1130 | GNUNET_free (huc->hello); | 1127 | GNUNET_free (huc->hello); |
1131 | GNUNET_free (huc->pid); | 1128 | GNUNET_free (huc->pid); |
@@ -1139,18 +1136,18 @@ merge_success (void *cls, int success) | |||
1139 | huc->wc = NULL; | 1136 | huc->wc = NULL; |
1140 | huc->cont (huc->cont_cls, GNUNET_OK); | 1137 | huc->cont (huc->cont_cls, GNUNET_OK); |
1141 | huc->success = GNUNET_OK; | 1138 | huc->success = GNUNET_OK; |
1142 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | 1139 | LOG (GNUNET_ERROR_TYPE_DEBUG, |
1143 | "Storing hello uri succeeded for peer %s!\n", | 1140 | "Storing hello uri succeeded for peer %s!\n", |
1144 | GNUNET_i2s (huc->pid)); | 1141 | GNUNET_i2s (huc->pid)); |
1145 | GNUNET_free (huc->hello); | 1142 | GNUNET_free (huc->hello); |
1146 | GNUNET_free (huc->pid); | 1143 | GNUNET_free (huc->pid); |
1147 | GNUNET_free (huc); | 1144 | GNUNET_free (huc); |
1148 | GNUNET_free (shu_cls); | 1145 | GNUNET_free (shu_cls); |
1149 | return; | 1146 | return; |
1150 | } | 1147 | } |
1151 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | 1148 | LOG (GNUNET_ERROR_TYPE_DEBUG, |
1152 | "Got notified during storing hello uri for peer %s!\n", | 1149 | "Got notified during storing hello uri for peer %s!\n", |
1153 | GNUNET_i2s (huc->pid)); | 1150 | GNUNET_i2s (huc->pid)); |
1154 | GNUNET_free (shu_cls); | 1151 | GNUNET_free (shu_cls); |
1155 | } | 1152 | } |
1156 | 1153 | ||
@@ -1176,9 +1173,9 @@ store_hello (struct GNUNET_PEERSTORE_StoreHelloContext *huc, | |||
1176 | GNUNET_PEERSTORE_STOREOPTION_REPLACE, | 1173 | GNUNET_PEERSTORE_STOREOPTION_REPLACE, |
1177 | merge_success, | 1174 | merge_success, |
1178 | shu_cls); | 1175 | shu_cls); |
1179 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | 1176 | LOG (GNUNET_ERROR_TYPE_DEBUG, |
1180 | "store_hello with expiration %s\n", | 1177 | "store_hello with expiration %s\n", |
1181 | GNUNET_STRINGS_absolute_time_to_string (hello_exp)); | 1178 | GNUNET_STRINGS_absolute_time_to_string (hello_exp)); |
1182 | GNUNET_assert (GNUNET_SYSERR != GNUNET_CONTAINER_multipeermap_put ( | 1179 | GNUNET_assert (GNUNET_SYSERR != GNUNET_CONTAINER_multipeermap_put ( |
1183 | huc->store_context_map, | 1180 | huc->store_context_map, |
1184 | huc->pid, | 1181 | huc->pid, |
@@ -1202,27 +1199,27 @@ merge_uri (void *cls, | |||
1202 | 1199 | ||
1203 | if (NULL != emsg) | 1200 | if (NULL != emsg) |
1204 | { | 1201 | { |
1205 | GNUNET_log (GNUNET_ERROR_TYPE_WARNING, | 1202 | LOG (GNUNET_ERROR_TYPE_WARNING, |
1206 | "Got failure from PEERSTORE: %s\n", | 1203 | "Got failure from PEERSTORE: %s\n", |
1207 | emsg); | 1204 | emsg); |
1208 | return; | 1205 | return; |
1209 | } | 1206 | } |
1210 | 1207 | ||
1211 | if (NULL == record && GNUNET_NO == huc->success) | 1208 | if (NULL == record && GNUNET_NO == huc->success) |
1212 | { | 1209 | { |
1213 | huc_hello_exp_time = GNUNET_HELLO_builder_get_expiration_time (huc->hello); | 1210 | huc_hello_exp_time = GNUNET_HELLO_builder_get_expiration_time (huc->hello); |
1214 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | 1211 | LOG (GNUNET_ERROR_TYPE_DEBUG, |
1215 | "merge_uri just store for peer %s with expiration %s\n", | 1212 | "merge_uri just store for peer %s with expiration %s\n", |
1216 | GNUNET_i2s (huc->pid), | 1213 | GNUNET_i2s (huc->pid), |
1217 | GNUNET_STRINGS_absolute_time_to_string (huc_hello_exp_time)); | 1214 | GNUNET_STRINGS_absolute_time_to_string (huc_hello_exp_time)); |
1218 | store_hello (huc, huc->hello); | 1215 | store_hello (huc, huc->hello); |
1219 | } | 1216 | } |
1220 | else if (GNUNET_NO == huc->success && 0 == GNUNET_memcmp (huc->pid, | 1217 | else if (GNUNET_NO == huc->success && 0 == GNUNET_memcmp (huc->pid, |
1221 | &record->peer)) | 1218 | &record->peer)) |
1222 | { | 1219 | { |
1223 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | 1220 | LOG (GNUNET_ERROR_TYPE_DEBUG, |
1224 | "merge_uri record for peer %s\n", | 1221 | "merge_uri record for peer %s\n", |
1225 | GNUNET_i2s (&record->peer)); | 1222 | GNUNET_i2s (&record->peer)); |
1226 | hello = record->value; | 1223 | hello = record->value; |
1227 | if ((0 == record->value_size)) | 1224 | if ((0 == record->value_size)) |
1228 | { | 1225 | { |
diff --git a/src/service/peerstore/peerstore_common.c b/src/service/peerstore/peerstore_common.c index e3bb77d86..5d4d06c0c 100644 --- a/src/service/peerstore/peerstore_common.c +++ b/src/service/peerstore/peerstore_common.c | |||
@@ -59,21 +59,9 @@ PEERSTORE_hash_key (const char *sub_system, | |||
59 | } | 59 | } |
60 | 60 | ||
61 | 61 | ||
62 | /** | ||
63 | * Creates a MQ envelope for a single record | ||
64 | * | ||
65 | * @param sub_system sub system string | ||
66 | * @param peer Peer identity (can be NULL) | ||
67 | * @param key record key string (can be NULL) | ||
68 | * @param value record value BLOB (can be NULL) | ||
69 | * @param value_size record value size in bytes (set to 0 if value is NULL) | ||
70 | * @param expiry time after which the record expires | ||
71 | * @param options options specific to the storage operation | ||
72 | * @param msg_type message type to be set in header | ||
73 | * @return pointer to record message struct | ||
74 | */ | ||
75 | struct GNUNET_MQ_Envelope * | 62 | struct GNUNET_MQ_Envelope * |
76 | PEERSTORE_create_record_mq_envelope (const char *sub_system, | 63 | PEERSTORE_create_record_mq_envelope (uint32_t rid, |
64 | const char *sub_system, | ||
77 | const struct GNUNET_PeerIdentity *peer, | 65 | const struct GNUNET_PeerIdentity *peer, |
78 | const char *key, | 66 | const char *key, |
79 | const void *value, | 67 | const void *value, |
@@ -106,6 +94,7 @@ PEERSTORE_create_record_mq_envelope (const char *sub_system, | |||
106 | srm->peer_set = htons (GNUNET_YES); | 94 | srm->peer_set = htons (GNUNET_YES); |
107 | srm->peer = *peer; | 95 | srm->peer = *peer; |
108 | } | 96 | } |
97 | srm->rid = rid; | ||
109 | srm->sub_system_size = htons (ss_size); | 98 | srm->sub_system_size = htons (ss_size); |
110 | srm->value_size = htons (value_size); | 99 | srm->value_size = htons (value_size); |
111 | srm->options = htonl (options); | 100 | srm->options = htonl (options); |
diff --git a/src/service/peerstore/peerstore_common.h b/src/service/peerstore/peerstore_common.h index f5352f5a5..56f1f8b8b 100644 --- a/src/service/peerstore/peerstore_common.h +++ b/src/service/peerstore/peerstore_common.h | |||
@@ -40,6 +40,7 @@ PEERSTORE_hash_key (const char *sub_system, | |||
40 | /** | 40 | /** |
41 | * Creates a MQ envelope for a single record | 41 | * Creates a MQ envelope for a single record |
42 | * | 42 | * |
43 | * @param rid request ID | ||
43 | * @param sub_system sub system string | 44 | * @param sub_system sub system string |
44 | * @param peer Peer identity (can be NULL) | 45 | * @param peer Peer identity (can be NULL) |
45 | * @param key record key string (can be NULL) | 46 | * @param key record key string (can be NULL) |
@@ -51,7 +52,8 @@ PEERSTORE_hash_key (const char *sub_system, | |||
51 | * @return pointer to record message struct | 52 | * @return pointer to record message struct |
52 | */ | 53 | */ |
53 | struct GNUNET_MQ_Envelope * | 54 | struct GNUNET_MQ_Envelope * |
54 | PEERSTORE_create_record_mq_envelope (const char *sub_system, | 55 | PEERSTORE_create_record_mq_envelope (uint32_t rid, |
56 | const char *sub_system, | ||
55 | const struct GNUNET_PeerIdentity *peer, | 57 | const struct GNUNET_PeerIdentity *peer, |
56 | const char *key, | 58 | const char *key, |
57 | const void *value, | 59 | const void *value, |
diff --git a/src/service/peerstore/perf_peerstore_store.c b/src/service/peerstore/perf_peerstore_store.c index e59af61e5..e328be93e 100644 --- a/src/service/peerstore/perf_peerstore_store.c +++ b/src/service/peerstore/perf_peerstore_store.c | |||
@@ -32,16 +32,20 @@ static int ok = 1; | |||
32 | 32 | ||
33 | static struct GNUNET_PEERSTORE_Handle *h; | 33 | static struct GNUNET_PEERSTORE_Handle *h; |
34 | 34 | ||
35 | static struct GNUNET_PEERSTORE_WatchContext *wc; | ||
36 | |||
35 | static char *ss = "test_peerstore_stress"; | 37 | static char *ss = "test_peerstore_stress"; |
36 | static struct GNUNET_PeerIdentity p; | 38 | static struct GNUNET_PeerIdentity p; |
37 | static char *k = "test_peerstore_stress_key"; | 39 | static char *k = "test_peerstore_stress_key"; |
38 | static char *v = "test_peerstore_stress_val"; | 40 | static char *v = "test_peerstore_stress_val"; |
39 | 41 | ||
40 | static int count = 0; | 42 | static int count = 0; |
43 | static int count_fin = 0; | ||
41 | 44 | ||
42 | static void | 45 | static void |
43 | disconnect () | 46 | disconnect (void *cls) |
44 | { | 47 | { |
48 | GNUNET_PEERSTORE_watch_cancel (wc); | ||
45 | if (NULL != h) | 49 | if (NULL != h) |
46 | GNUNET_PEERSTORE_disconnect (h); | 50 | GNUNET_PEERSTORE_disconnect (h); |
47 | GNUNET_SCHEDULER_shutdown (); | 51 | GNUNET_SCHEDULER_shutdown (); |
@@ -49,14 +53,27 @@ disconnect () | |||
49 | 53 | ||
50 | 54 | ||
51 | static void | 55 | static void |
56 | store_cont (void *cls, int ret) | ||
57 | { | ||
58 | count_fin++; | ||
59 | if (count_fin == count) | ||
60 | { | ||
61 | ok = 0; | ||
62 | GNUNET_SCHEDULER_add_now (&disconnect, NULL); | ||
63 | } | ||
64 | } | ||
65 | |||
66 | |||
67 | static void | ||
52 | store () | 68 | store () |
53 | { | 69 | { |
70 | count++; | ||
54 | GNUNET_PEERSTORE_store (h, ss, &p, k, v, strlen (v) + 1, | 71 | GNUNET_PEERSTORE_store (h, ss, &p, k, v, strlen (v) + 1, |
55 | GNUNET_TIME_UNIT_FOREVER_ABS, | 72 | GNUNET_TIME_UNIT_FOREVER_ABS, |
56 | (count == | 73 | (count == |
57 | 0) ? GNUNET_PEERSTORE_STOREOPTION_REPLACE : | 74 | 0) ? GNUNET_PEERSTORE_STOREOPTION_REPLACE : |
58 | GNUNET_PEERSTORE_STOREOPTION_MULTIPLE, NULL, NULL); | 75 | GNUNET_PEERSTORE_STOREOPTION_MULTIPLE, store_cont, |
59 | count++; | 76 | NULL); |
60 | } | 77 | } |
61 | 78 | ||
62 | 79 | ||
@@ -65,12 +82,7 @@ watch_cb (void *cls, const struct GNUNET_PEERSTORE_Record *record, | |||
65 | const char *emsg) | 82 | const char *emsg) |
66 | { | 83 | { |
67 | GNUNET_assert (NULL == emsg); | 84 | GNUNET_assert (NULL == emsg); |
68 | if (STORES == count) | 85 | if (STORES > count) |
69 | { | ||
70 | ok = 0; | ||
71 | disconnect (); | ||
72 | } | ||
73 | else | ||
74 | store (); | 86 | store (); |
75 | } | 87 | } |
76 | 88 | ||
@@ -82,7 +94,7 @@ run (void *cls, const struct GNUNET_CONFIGURATION_Handle *cfg, | |||
82 | memset (&p, 5, sizeof(p)); | 94 | memset (&p, 5, sizeof(p)); |
83 | h = GNUNET_PEERSTORE_connect (cfg); | 95 | h = GNUNET_PEERSTORE_connect (cfg); |
84 | GNUNET_assert (NULL != h); | 96 | GNUNET_assert (NULL != h); |
85 | GNUNET_PEERSTORE_watch (h, ss, &p, k, &watch_cb, NULL); | 97 | wc = GNUNET_PEERSTORE_watch (h, ss, &p, k, &watch_cb, NULL); |
86 | store (); | 98 | store (); |
87 | } | 99 | } |
88 | 100 | ||
diff --git a/src/service/peerstore/test_peerstore_api_iterate.c b/src/service/peerstore/test_peerstore_api_iterate.c index 59367a110..0fa58f3fd 100644 --- a/src/service/peerstore/test_peerstore_api_iterate.c +++ b/src/service/peerstore/test_peerstore_api_iterate.c | |||
@@ -21,6 +21,7 @@ | |||
21 | * @file peerstore/test_peerstore_api_iterate.c | 21 | * @file peerstore/test_peerstore_api_iterate.c |
22 | * @brief testcase for peerstore iteration operation | 22 | * @brief testcase for peerstore iteration operation |
23 | */ | 23 | */ |
24 | #include "gnunet_common.h" | ||
24 | #include "platform.h" | 25 | #include "platform.h" |
25 | #include "gnunet_util_lib.h" | 26 | #include "gnunet_util_lib.h" |
26 | #include "gnunet_testing_lib.h" | 27 | #include "gnunet_testing_lib.h" |
@@ -40,6 +41,13 @@ static char *k3 = "test_peerstore_api_iterate_key3"; | |||
40 | static char *val = "test_peerstore_api_iterate_val"; | 41 | static char *val = "test_peerstore_api_iterate_val"; |
41 | static int count = 0; | 42 | static int count = 0; |
42 | 43 | ||
44 | static void | ||
45 | finish (void *cls) | ||
46 | { | ||
47 | GNUNET_PEERSTORE_disconnect (h); | ||
48 | GNUNET_SCHEDULER_shutdown (); | ||
49 | } | ||
50 | |||
43 | 51 | ||
44 | static void | 52 | static void |
45 | iter3_cb (void *cls, | 53 | iter3_cb (void *cls, |
@@ -58,8 +66,7 @@ iter3_cb (void *cls, | |||
58 | } | 66 | } |
59 | GNUNET_assert (count == 3); | 67 | GNUNET_assert (count == 3); |
60 | ok = 0; | 68 | ok = 0; |
61 | GNUNET_PEERSTORE_disconnect (h); | 69 | GNUNET_SCHEDULER_add_now (&finish, NULL); |
62 | GNUNET_SCHEDULER_shutdown (); | ||
63 | } | 70 | } |
64 | 71 | ||
65 | 72 | ||
@@ -104,6 +111,7 @@ iter1_cb (void *cls, | |||
104 | count++; | 111 | count++; |
105 | return; | 112 | return; |
106 | } | 113 | } |
114 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "%u is count\n", count); | ||
107 | GNUNET_assert (count == 1); | 115 | GNUNET_assert (count == 1); |
108 | count = 0; | 116 | count = 0; |
109 | ic = GNUNET_PEERSTORE_iterate (h, | 117 | ic = GNUNET_PEERSTORE_iterate (h, |
@@ -116,6 +124,50 @@ iter1_cb (void *cls, | |||
116 | 124 | ||
117 | 125 | ||
118 | static void | 126 | static void |
127 | store_cont (void *cls, int success) | ||
128 | { | ||
129 | GNUNET_assert (GNUNET_OK == success); | ||
130 | if (0 == count) | ||
131 | { | ||
132 | GNUNET_PEERSTORE_store (h, | ||
133 | ss, | ||
134 | &p1, | ||
135 | k2, | ||
136 | val, | ||
137 | strlen (val) + 1, | ||
138 | GNUNET_TIME_UNIT_FOREVER_ABS, | ||
139 | GNUNET_PEERSTORE_STOREOPTION_REPLACE, | ||
140 | &store_cont, | ||
141 | NULL); | ||
142 | } | ||
143 | else if (1 == count) | ||
144 | { | ||
145 | GNUNET_PEERSTORE_store (h, | ||
146 | ss, | ||
147 | &p2, | ||
148 | k3, | ||
149 | val, | ||
150 | strlen (val) + 1, | ||
151 | GNUNET_TIME_UNIT_FOREVER_ABS, | ||
152 | GNUNET_PEERSTORE_STOREOPTION_REPLACE, | ||
153 | &store_cont, | ||
154 | NULL); | ||
155 | } | ||
156 | else | ||
157 | { | ||
158 | count = 0; | ||
159 | ic = GNUNET_PEERSTORE_iterate (h, | ||
160 | ss, | ||
161 | &p1, | ||
162 | k1, | ||
163 | &iter1_cb, NULL); | ||
164 | return; | ||
165 | } | ||
166 | count++; | ||
167 | } | ||
168 | |||
169 | |||
170 | static void | ||
119 | run (void *cls, | 171 | run (void *cls, |
120 | const struct GNUNET_CONFIGURATION_Handle *cfg, | 172 | const struct GNUNET_CONFIGURATION_Handle *cfg, |
121 | struct GNUNET_TESTING_Peer *peer) | 173 | struct GNUNET_TESTING_Peer *peer) |
@@ -124,6 +176,7 @@ run (void *cls, | |||
124 | GNUNET_assert (NULL != h); | 176 | GNUNET_assert (NULL != h); |
125 | memset (&p1, 1, sizeof(p1)); | 177 | memset (&p1, 1, sizeof(p1)); |
126 | memset (&p2, 2, sizeof(p2)); | 178 | memset (&p2, 2, sizeof(p2)); |
179 | count = 0; | ||
127 | GNUNET_PEERSTORE_store (h, | 180 | GNUNET_PEERSTORE_store (h, |
128 | ss, | 181 | ss, |
129 | &p1, | 182 | &p1, |
@@ -132,33 +185,8 @@ run (void *cls, | |||
132 | strlen (val) + 1, | 185 | strlen (val) + 1, |
133 | GNUNET_TIME_UNIT_FOREVER_ABS, | 186 | GNUNET_TIME_UNIT_FOREVER_ABS, |
134 | GNUNET_PEERSTORE_STOREOPTION_REPLACE, | 187 | GNUNET_PEERSTORE_STOREOPTION_REPLACE, |
135 | NULL, | 188 | &store_cont, |
136 | NULL); | ||
137 | GNUNET_PEERSTORE_store (h, | ||
138 | ss, | ||
139 | &p1, | ||
140 | k2, | ||
141 | val, | ||
142 | strlen (val) + 1, | ||
143 | GNUNET_TIME_UNIT_FOREVER_ABS, | ||
144 | GNUNET_PEERSTORE_STOREOPTION_REPLACE, | ||
145 | NULL, | ||
146 | NULL); | 189 | NULL); |
147 | GNUNET_PEERSTORE_store (h, | ||
148 | ss, | ||
149 | &p2, | ||
150 | k3, | ||
151 | val, | ||
152 | strlen (val) + 1, | ||
153 | GNUNET_TIME_UNIT_FOREVER_ABS, | ||
154 | GNUNET_PEERSTORE_STOREOPTION_REPLACE, | ||
155 | NULL, | ||
156 | NULL); | ||
157 | ic = GNUNET_PEERSTORE_iterate (h, | ||
158 | ss, | ||
159 | &p1, | ||
160 | k1, | ||
161 | &iter1_cb, NULL); | ||
162 | } | 190 | } |
163 | 191 | ||
164 | 192 | ||
diff --git a/src/service/peerstore/test_peerstore_api_store.c b/src/service/peerstore/test_peerstore_api_store.c index 77e8a17c1..8cf0e60a7 100644 --- a/src/service/peerstore/test_peerstore_api_store.c +++ b/src/service/peerstore/test_peerstore_api_store.c | |||
@@ -21,6 +21,7 @@ | |||
21 | * @file peerstore/test_peerstore_api_store.c | 21 | * @file peerstore/test_peerstore_api_store.c |
22 | * @brief testcase for peerstore store operation | 22 | * @brief testcase for peerstore store operation |
23 | */ | 23 | */ |
24 | #include "gnunet_common.h" | ||
24 | #include "platform.h" | 25 | #include "platform.h" |
25 | #include "gnunet_peerstore_service.h" | 26 | #include "gnunet_peerstore_service.h" |
26 | #include "gnunet_testing_lib.h" | 27 | #include "gnunet_testing_lib.h" |
@@ -41,6 +42,13 @@ static int count = 0; | |||
41 | 42 | ||
42 | 43 | ||
43 | static void | 44 | static void |
45 | finish (void *cls) | ||
46 | { | ||
47 | GNUNET_PEERSTORE_disconnect (h); | ||
48 | GNUNET_SCHEDULER_shutdown (); | ||
49 | } | ||
50 | |||
51 | static void | ||
44 | test3_cont2 (void *cls, | 52 | test3_cont2 (void *cls, |
45 | const struct GNUNET_PEERSTORE_Record *record, | 53 | const struct GNUNET_PEERSTORE_Record *record, |
46 | const char *emsg) | 54 | const char *emsg) |
@@ -57,8 +65,7 @@ test3_cont2 (void *cls, | |||
57 | } | 65 | } |
58 | GNUNET_assert (count == 1); | 66 | GNUNET_assert (count == 1); |
59 | ok = 0; | 67 | ok = 0; |
60 | GNUNET_PEERSTORE_disconnect (h, GNUNET_YES); | 68 | GNUNET_SCHEDULER_add_now (&finish, NULL); |
61 | GNUNET_SCHEDULER_shutdown (); | ||
62 | } | 69 | } |
63 | 70 | ||
64 | 71 | ||
@@ -158,7 +165,10 @@ test1_cont2 (void *cls, | |||
158 | const char *emsg) | 165 | const char *emsg) |
159 | { | 166 | { |
160 | if (NULL != emsg) | 167 | if (NULL != emsg) |
168 | { | ||
169 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, "Error received: %s\n", emsg); | ||
161 | return; | 170 | return; |
171 | } | ||
162 | if (NULL != record) | 172 | if (NULL != record) |
163 | { | 173 | { |
164 | GNUNET_assert ((strlen (val1) + 1) == record->value_size); | 174 | GNUNET_assert ((strlen (val1) + 1) == record->value_size); |
@@ -175,6 +185,7 @@ test1_cont2 (void *cls, | |||
175 | static void | 185 | static void |
176 | test1_cont (void *cls, int success) | 186 | test1_cont (void *cls, int success) |
177 | { | 187 | { |
188 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Store done, ret=%d...\n", success); | ||
178 | if (GNUNET_YES != success) | 189 | if (GNUNET_YES != success) |
179 | return; | 190 | return; |
180 | count = 0; | 191 | count = 0; |
@@ -193,6 +204,7 @@ test1_cont (void *cls, int success) | |||
193 | static void | 204 | static void |
194 | test1 () | 205 | test1 () |
195 | { | 206 | { |
207 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "test1 start\n"); | ||
196 | GNUNET_PEERSTORE_store (h, | 208 | GNUNET_PEERSTORE_store (h, |
197 | subsystem, | 209 | subsystem, |
198 | &pid, | 210 | &pid, |
diff --git a/src/service/peerstore/test_peerstore_api_sync.c b/src/service/peerstore/test_peerstore_api_sync.c deleted file mode 100644 index 4e16afae8..000000000 --- a/src/service/peerstore/test_peerstore_api_sync.c +++ /dev/null | |||
@@ -1,252 +0,0 @@ | |||
1 | /* | ||
2 | This file is part of GNUnet. | ||
3 | Copyright (C) 2015 GNUnet e.V. | ||
4 | |||
5 | GNUnet is free software: you can redistribute it and/or modify it | ||
6 | under the terms of the GNU Affero General Public License as published | ||
7 | by the Free Software Foundation, either version 3 of the License, | ||
8 | or (at your option) any later version. | ||
9 | |||
10 | GNUnet is distributed in the hope that it will be useful, but | ||
11 | WITHOUT ANY WARRANTY; without even the implied warranty of | ||
12 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | ||
13 | Affero General Public License for more details. | ||
14 | |||
15 | You should have received a copy of the GNU Affero General Public License | ||
16 | along with this program. If not, see <http://www.gnu.org/licenses/>. | ||
17 | |||
18 | SPDX-License-Identifier: AGPL3.0-or-later | ||
19 | */ | ||
20 | /** | ||
21 | * @file peerstore/test_peerstore_api_sync.c | ||
22 | * @brief testcase for peerstore sync-on-disconnect feature. Stores | ||
23 | * a value just before disconnecting, and then checks that | ||
24 | * this value is actually stored. | ||
25 | * @author Omar Tarabai | ||
26 | * @author Christian Grothoff (minor fix, comments) | ||
27 | */ | ||
28 | #include "platform.h" | ||
29 | #include "gnunet_util_lib.h" | ||
30 | #include "gnunet_testing_lib.h" | ||
31 | #include "gnunet_peerstore_service.h" | ||
32 | |||
33 | /** | ||
34 | * Overall result, 0 for success. | ||
35 | */ | ||
36 | static int ok = 404; | ||
37 | |||
38 | /** | ||
39 | * Configuration we use. | ||
40 | */ | ||
41 | static const struct GNUNET_CONFIGURATION_Handle *cfg; | ||
42 | |||
43 | /** | ||
44 | * handle to talk to the peerstore. | ||
45 | */ | ||
46 | static struct GNUNET_PEERSTORE_Handle *h; | ||
47 | |||
48 | /** | ||
49 | * Subsystem we store the value for. | ||
50 | */ | ||
51 | static const char *subsystem = "test_peerstore_api_sync"; | ||
52 | |||
53 | /** | ||
54 | * Fake PID under which we store the value. | ||
55 | */ | ||
56 | static struct GNUNET_PeerIdentity pid; | ||
57 | |||
58 | /** | ||
59 | * Test key we're storing the test value under. | ||
60 | */ | ||
61 | static const char *key = "test_peerstore_api_store_key"; | ||
62 | |||
63 | /** | ||
64 | * Test value we are storing. | ||
65 | */ | ||
66 | static const char *val = "test_peerstore_api_store_val"; | ||
67 | |||
68 | |||
69 | /** | ||
70 | * Timeout | ||
71 | */ | ||
72 | #define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 10) | ||
73 | |||
74 | /** | ||
75 | * Timeout task | ||
76 | */ | ||
77 | static struct GNUNET_SCHEDULER_Task *to; | ||
78 | |||
79 | /** | ||
80 | * Iterate handle | ||
81 | */ | ||
82 | static struct GNUNET_PEERSTORE_IterateContext *it; | ||
83 | |||
84 | static void | ||
85 | test_cont (void *cls); | ||
86 | |||
87 | /** | ||
88 | * Function that should be called with the result of the | ||
89 | * lookup, and finally once with NULL to signal the end | ||
90 | * of the iteration. | ||
91 | * | ||
92 | * Upon the first call, we set "ok" to success. On the | ||
93 | * second call (end of iteration) we terminate the test. | ||
94 | * | ||
95 | * @param cls NULL | ||
96 | * @param record the information stored in the peerstore | ||
97 | * @param emsg any error message | ||
98 | * @return #GNUNET_YES (all good, continue) | ||
99 | */ | ||
100 | static void | ||
101 | iterate_cb (void *cls, | ||
102 | const struct GNUNET_PEERSTORE_Record *record, | ||
103 | const char *emsg) | ||
104 | { | ||
105 | const char *rec_val; | ||
106 | |||
107 | GNUNET_break (NULL == emsg); | ||
108 | if (NULL == record) | ||
109 | { | ||
110 | it = NULL; | ||
111 | if (0 == ok) | ||
112 | { | ||
113 | GNUNET_PEERSTORE_disconnect (h); | ||
114 | if (NULL != to) | ||
115 | { | ||
116 | GNUNET_SCHEDULER_cancel (to); | ||
117 | to = NULL; | ||
118 | } | ||
119 | GNUNET_SCHEDULER_shutdown (); | ||
120 | return; | ||
121 | } | ||
122 | /** | ||
123 | * Try again | ||
124 | */ | ||
125 | GNUNET_SCHEDULER_add_now (&test_cont, | ||
126 | NULL); | ||
127 | return; | ||
128 | } | ||
129 | rec_val = record->value; | ||
130 | GNUNET_break (0 == strcmp (rec_val, val)); | ||
131 | ok = 0; | ||
132 | } | ||
133 | |||
134 | |||
135 | static void | ||
136 | timeout_task (void *cls) | ||
137 | { | ||
138 | to = NULL; | ||
139 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, | ||
140 | "Timeout reached\n"); | ||
141 | if (NULL != it) | ||
142 | GNUNET_PEERSTORE_iterate_cancel (it); | ||
143 | it = NULL; | ||
144 | GNUNET_PEERSTORE_disconnect (h, | ||
145 | GNUNET_NO); | ||
146 | GNUNET_SCHEDULER_shutdown (); | ||
147 | return; | ||
148 | } | ||
149 | |||
150 | |||
151 | /** | ||
152 | * Run the 2nd stage of the test where we fetch the | ||
153 | * data that should have been stored. | ||
154 | * | ||
155 | * @param cls NULL | ||
156 | */ | ||
157 | static void | ||
158 | test_cont (void *cls) | ||
159 | { | ||
160 | it = GNUNET_PEERSTORE_iterate (h, | ||
161 | subsystem, | ||
162 | &pid, key, | ||
163 | &iterate_cb, | ||
164 | NULL); | ||
165 | } | ||
166 | |||
167 | |||
168 | static void | ||
169 | disc_cont (void *cls) | ||
170 | { | ||
171 | GNUNET_PEERSTORE_disconnect (h, GNUNET_YES); | ||
172 | h = GNUNET_PEERSTORE_connect (cfg); | ||
173 | GNUNET_SCHEDULER_add_now (&test_cont, | ||
174 | NULL); | ||
175 | } | ||
176 | |||
177 | |||
178 | static void | ||
179 | store_cont (void *cls, int success) | ||
180 | { | ||
181 | ok = success; | ||
182 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
183 | "Success: %s\n", | ||
184 | (GNUNET_SYSERR == ok) ? "no" : "yes"); | ||
185 | /* We need to wait a little bit to give the disconnect | ||
186 | a chance to actually finish the operation; otherwise, | ||
187 | the test may fail non-deterministically if the new | ||
188 | connection is faster than the cleanup routine of the | ||
189 | old one. */ | ||
190 | GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_SECONDS, | ||
191 | &disc_cont, | ||
192 | NULL); | ||
193 | } | ||
194 | |||
195 | |||
196 | /** | ||
197 | * Actually run the test. | ||
198 | */ | ||
199 | static void | ||
200 | test1 () | ||
201 | { | ||
202 | h = GNUNET_PEERSTORE_connect (cfg); | ||
203 | GNUNET_PEERSTORE_store (h, | ||
204 | subsystem, | ||
205 | &pid, | ||
206 | key, | ||
207 | val, strlen (val) + 1, | ||
208 | GNUNET_TIME_UNIT_FOREVER_ABS, | ||
209 | GNUNET_PEERSTORE_STOREOPTION_REPLACE, | ||
210 | &store_cont, NULL); | ||
211 | } | ||
212 | |||
213 | |||
214 | /** | ||
215 | * Initialize globals and launch the test. | ||
216 | * | ||
217 | * @param cls NULL | ||
218 | * @param c configuration to use | ||
219 | * @param peer handle to our peer (unused) | ||
220 | */ | ||
221 | static void | ||
222 | run (void *cls, | ||
223 | const struct GNUNET_CONFIGURATION_Handle *c, | ||
224 | struct GNUNET_TESTING_Peer *peer) | ||
225 | { | ||
226 | cfg = c; | ||
227 | memset (&pid, 1, sizeof(pid)); | ||
228 | to = GNUNET_SCHEDULER_add_delayed (TIMEOUT, | ||
229 | &timeout_task, | ||
230 | NULL); | ||
231 | GNUNET_SCHEDULER_add_now (&test1, NULL); | ||
232 | } | ||
233 | |||
234 | |||
235 | int | ||
236 | main (int argc, char *argv[]) | ||
237 | { | ||
238 | if (0 != | ||
239 | GNUNET_TESTING_service_run ("test-gnunet-peerstore-sync", | ||
240 | "peerstore", | ||
241 | "peerstore.conf", | ||
242 | &run, NULL)) | ||
243 | return 1; | ||
244 | if (0 != ok) | ||
245 | fprintf (stderr, | ||
246 | "Test failed: %d\n", | ||
247 | ok); | ||
248 | return ok; | ||
249 | } | ||
250 | |||
251 | |||
252 | /* end of test_peerstore_api_sync.c */ | ||
diff --git a/src/service/peerstore/test_peerstore_api_watch.c b/src/service/peerstore/test_peerstore_api_watch.c index 126b321df..63b0e896b 100644 --- a/src/service/peerstore/test_peerstore_api_watch.c +++ b/src/service/peerstore/test_peerstore_api_watch.c | |||
@@ -21,6 +21,8 @@ | |||
21 | * @file peerstore/test_peerstore_api_watch.c | 21 | * @file peerstore/test_peerstore_api_watch.c |
22 | * @brief testcase for peerstore watch functionality | 22 | * @brief testcase for peerstore watch functionality |
23 | */ | 23 | */ |
24 | #include "gnunet_common.h" | ||
25 | #include "gnunet_time_lib.h" | ||
24 | #include "platform.h" | 26 | #include "platform.h" |
25 | #include "gnunet_util_lib.h" | 27 | #include "gnunet_util_lib.h" |
26 | #include "gnunet_testing_lib.h" | 28 | #include "gnunet_testing_lib.h" |
@@ -31,12 +33,42 @@ static int ok = 1; | |||
31 | 33 | ||
32 | static struct GNUNET_PEERSTORE_Handle *h; | 34 | static struct GNUNET_PEERSTORE_Handle *h; |
33 | 35 | ||
36 | static struct GNUNET_PEERSTORE_WatchContext *wc; | ||
37 | |||
34 | static char *ss = "test_peerstore_api_watch"; | 38 | static char *ss = "test_peerstore_api_watch"; |
35 | 39 | ||
36 | static char *k = "test_peerstore_api_watch_key"; | 40 | static char *k = "test_peerstore_api_watch_key"; |
37 | 41 | ||
38 | static char *val = "test_peerstore_api_watch_val"; | 42 | static char *val = "test_peerstore_api_watch_val"; |
39 | 43 | ||
44 | static struct GNUNET_PeerIdentity p; | ||
45 | |||
46 | static void | ||
47 | finish (void *cls) | ||
48 | { | ||
49 | GNUNET_PEERSTORE_watch_cancel (wc); | ||
50 | GNUNET_PEERSTORE_disconnect (h); | ||
51 | GNUNET_SCHEDULER_shutdown (); | ||
52 | } | ||
53 | |||
54 | |||
55 | static void | ||
56 | cont (void *cls) | ||
57 | { | ||
58 | GNUNET_PEERSTORE_store (h, | ||
59 | ss, | ||
60 | &p, | ||
61 | k, | ||
62 | val, | ||
63 | strlen (val) + 1, | ||
64 | GNUNET_TIME_UNIT_FOREVER_ABS, | ||
65 | GNUNET_PEERSTORE_STOREOPTION_REPLACE, | ||
66 | NULL, | ||
67 | NULL); | ||
68 | } | ||
69 | |||
70 | |||
71 | static int initial_iteration = GNUNET_YES; | ||
40 | 72 | ||
41 | static void | 73 | static void |
42 | watch_cb (void *cls, | 74 | watch_cb (void *cls, |
@@ -44,12 +76,28 @@ watch_cb (void *cls, | |||
44 | const char *emsg) | 76 | const char *emsg) |
45 | { | 77 | { |
46 | GNUNET_assert (NULL == emsg); | 78 | GNUNET_assert (NULL == emsg); |
79 | if (GNUNET_YES == initial_iteration) | ||
80 | { | ||
81 | if (NULL != record) | ||
82 | { | ||
83 | GNUNET_break (0); | ||
84 | return; // Ignore this record, FIXME: Test unclean | ||
85 | } | ||
86 | GNUNET_SCHEDULER_add_delayed (GNUNET_TIME_UNIT_SECONDS, &cont, NULL); | ||
87 | initial_iteration = GNUNET_NO; | ||
88 | return; | ||
89 | } | ||
90 | if (NULL == record) | ||
91 | { | ||
92 | GNUNET_break (0); | ||
93 | return; | ||
94 | } | ||
95 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, "Received record: %s\n", | ||
96 | (char*) record->value); | ||
47 | GNUNET_assert (0 == strcmp (val, | 97 | GNUNET_assert (0 == strcmp (val, |
48 | (char *) record->value)); | 98 | (char *) record->value)); |
49 | ok = 0; | 99 | ok = 0; |
50 | GNUNET_PEERSTORE_disconnect (h, | 100 | GNUNET_SCHEDULER_add_now (&finish, NULL); |
51 | GNUNET_NO); | ||
52 | GNUNET_SCHEDULER_shutdown (); | ||
53 | } | 101 | } |
54 | 102 | ||
55 | 103 | ||
@@ -58,29 +106,18 @@ run (void *cls, | |||
58 | const struct GNUNET_CONFIGURATION_Handle *cfg, | 106 | const struct GNUNET_CONFIGURATION_Handle *cfg, |
59 | struct GNUNET_TESTING_Peer *peer) | 107 | struct GNUNET_TESTING_Peer *peer) |
60 | { | 108 | { |
61 | struct GNUNET_PeerIdentity p; | ||
62 | 109 | ||
63 | h = GNUNET_PEERSTORE_connect (cfg); | 110 | h = GNUNET_PEERSTORE_connect (cfg); |
64 | GNUNET_assert (NULL != h); | 111 | GNUNET_assert (NULL != h); |
65 | memset (&p, | 112 | memset (&p, |
66 | 4, | 113 | 4, |
67 | sizeof(p)); | 114 | sizeof(p)); |
68 | GNUNET_PEERSTORE_watch (h, | 115 | wc = GNUNET_PEERSTORE_watch (h, |
69 | ss, | 116 | ss, |
70 | &p, | 117 | &p, |
71 | k, | 118 | k, |
72 | &watch_cb, | 119 | &watch_cb, |
73 | NULL); | 120 | NULL); |
74 | GNUNET_PEERSTORE_store (h, | ||
75 | ss, | ||
76 | &p, | ||
77 | k, | ||
78 | val, | ||
79 | strlen (val) + 1, | ||
80 | GNUNET_TIME_UNIT_FOREVER_ABS, | ||
81 | GNUNET_PEERSTORE_STOREOPTION_REPLACE, | ||
82 | NULL, | ||
83 | NULL); | ||
84 | } | 121 | } |
85 | 122 | ||
86 | 123 | ||