diff options
author | Christian Grothoff <christian@grothoff.org> | 2009-07-25 14:30:10 +0000 |
---|---|---|
committer | Christian Grothoff <christian@grothoff.org> | 2009-07-25 14:30:10 +0000 |
commit | 4f3705cbfef52322292ce8b60f1d5326825f8606 (patch) | |
tree | d46c3294cb791d674ab63829d3559c9a162404f1 /src/datastore | |
parent | a8871b8ff983bdb8adc224a9a88ba5d2960df859 (diff) | |
download | gnunet-4f3705cbfef52322292ce8b60f1d5326825f8606.tar.gz gnunet-4f3705cbfef52322292ce8b60f1d5326825f8606.zip |
more tests
Diffstat (limited to 'src/datastore')
-rw-r--r-- | src/datastore/Makefile.am | 7 | ||||
-rw-r--r-- | src/datastore/datastore.h | 2 | ||||
-rw-r--r-- | src/datastore/datastore_api.c | 13 | ||||
-rw-r--r-- | src/datastore/gnunet-service-datastore.c | 8 | ||||
-rw-r--r-- | src/datastore/plugin_datastore_sqlite.c | 8 | ||||
-rw-r--r-- | src/datastore/test_datastore_api.c | 189 | ||||
-rw-r--r-- | src/datastore/test_datastore_api_management.c | 377 |
7 files changed, 580 insertions, 24 deletions
diff --git a/src/datastore/Makefile.am b/src/datastore/Makefile.am index 17fdb4378..07a14e534 100644 --- a/src/datastore/Makefile.am +++ b/src/datastore/Makefile.am | |||
@@ -58,6 +58,7 @@ libgnunet_plugin_datastore_template_la_LDFLAGS = \ | |||
58 | 58 | ||
59 | check_PROGRAMS = \ | 59 | check_PROGRAMS = \ |
60 | test_datastore_api \ | 60 | test_datastore_api \ |
61 | test_datastore_api_management \ | ||
61 | perf_datastore_api \ | 62 | perf_datastore_api \ |
62 | perf_plugin_datastore | 63 | perf_plugin_datastore |
63 | 64 | ||
@@ -69,6 +70,12 @@ test_datastore_api_LDADD = \ | |||
69 | $(top_builddir)/src/datastore/libgnunetdatastore.la \ | 70 | $(top_builddir)/src/datastore/libgnunetdatastore.la \ |
70 | $(top_builddir)/src/util/libgnunetutil.la | 71 | $(top_builddir)/src/util/libgnunetutil.la |
71 | 72 | ||
73 | test_datastore_api_management_SOURCES = \ | ||
74 | test_datastore_api_management.c | ||
75 | test_datastore_api_management_LDADD = \ | ||
76 | $(top_builddir)/src/datastore/libgnunetdatastore.la \ | ||
77 | $(top_builddir)/src/util/libgnunetutil.la | ||
78 | |||
72 | perf_datastore_api_SOURCES = \ | 79 | perf_datastore_api_SOURCES = \ |
73 | perf_datastore_api.c | 80 | perf_datastore_api.c |
74 | perf_datastore_api_LDADD = \ | 81 | perf_datastore_api_LDADD = \ |
diff --git a/src/datastore/datastore.h b/src/datastore/datastore.h index f1da17ee4..aa2646c0a 100644 --- a/src/datastore/datastore.h +++ b/src/datastore/datastore.h | |||
@@ -19,7 +19,7 @@ | |||
19 | */ | 19 | */ |
20 | 20 | ||
21 | /** | 21 | /** |
22 | * @file datastore/datastore.hc | 22 | * @file datastore/datastore.h |
23 | * @brief structs for communication between datastore service and API | 23 | * @brief structs for communication between datastore service and API |
24 | * @author Christian Grothoff | 24 | * @author Christian Grothoff |
25 | */ | 25 | */ |
diff --git a/src/datastore/datastore_api.c b/src/datastore/datastore_api.c index f9a28800c..361f76e4a 100644 --- a/src/datastore/datastore_api.c +++ b/src/datastore/datastore_api.c | |||
@@ -204,16 +204,21 @@ with_status_response_handler (void *cls, | |||
204 | sm = (const struct StatusMessage*) msg; | 204 | sm = (const struct StatusMessage*) msg; |
205 | status = ntohl(sm->status); | 205 | status = ntohl(sm->status); |
206 | emsg = NULL; | 206 | emsg = NULL; |
207 | if (status == GNUNET_SYSERR) | 207 | if (ntohs(msg->size) > sizeof(struct StatusMessage)) |
208 | { | 208 | { |
209 | emsg = (const char*) &sm[1]; | 209 | emsg = (const char*) &sm[1]; |
210 | if ( (ntohs(msg->size) == sizeof(struct StatusMessage)) || | 210 | if (emsg[ntohs(msg->size) - sizeof(struct StatusMessage) - 1] != '\0') |
211 | (emsg[ntohs(msg->size) - sizeof(struct StatusMessage) - 1] != '\0') ) | ||
212 | { | 211 | { |
213 | GNUNET_break (0); | 212 | GNUNET_break (0); |
214 | emsg = _("Invalid error message received from datastore service"); | 213 | emsg = _("Invalid error message received from datastore service"); |
215 | } | 214 | } |
216 | } | 215 | } |
216 | if ( (status == GNUNET_SYSERR) && | ||
217 | (emsg == NULL) ) | ||
218 | { | ||
219 | GNUNET_break (0); | ||
220 | emsg = _("Invalid error message received from datastore service"); | ||
221 | } | ||
217 | h->response_proc = NULL; | 222 | h->response_proc = NULL; |
218 | #if DEBUG_DATASTORE | 223 | #if DEBUG_DATASTORE |
219 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | 224 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
@@ -408,7 +413,7 @@ GNUNET_DATASTORE_reserve (struct GNUNET_DATASTORE_Handle *h, | |||
408 | rm->header.type = htons(GNUNET_MESSAGE_TYPE_DATASTORE_RESERVE); | 413 | rm->header.type = htons(GNUNET_MESSAGE_TYPE_DATASTORE_RESERVE); |
409 | rm->header.size = htons(sizeof (struct ReserveMessage)); | 414 | rm->header.size = htons(sizeof (struct ReserveMessage)); |
410 | rm->entries = htonl(entries); | 415 | rm->entries = htonl(entries); |
411 | rm->amount = htonl(amount); | 416 | rm->amount = GNUNET_htonll(amount); |
412 | transmit_for_status (h, cont, cont_cls, timeout); | 417 | transmit_for_status (h, cont, cont_cls, timeout); |
413 | } | 418 | } |
414 | 419 | ||
diff --git a/src/datastore/gnunet-service-datastore.c b/src/datastore/gnunet-service-datastore.c index 77047dc8a..22ae6feb5 100644 --- a/src/datastore/gnunet-service-datastore.c +++ b/src/datastore/gnunet-service-datastore.c | |||
@@ -513,7 +513,7 @@ transmit_status (struct GNUNET_SERVER_Client *client, | |||
513 | 513 | ||
514 | #if DEBUG_DATASTORE | 514 | #if DEBUG_DATASTORE |
515 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | 515 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
516 | "Transmitting `%s' message with value %d and message %s\n", | 516 | "Transmitting `%s' message with value %d and message `%s'\n", |
517 | "STATUS", | 517 | "STATUS", |
518 | code, | 518 | code, |
519 | msg != NULL ? msg : "(none)"); | 519 | msg != NULL ? msg : "(none)"); |
@@ -639,15 +639,15 @@ handle_reserve (void *cls, | |||
639 | unsigned long long used; | 639 | unsigned long long used; |
640 | unsigned long long req; | 640 | unsigned long long req; |
641 | uint64_t amount; | 641 | uint64_t amount; |
642 | uint64_t entries; | 642 | uint32_t entries; |
643 | 643 | ||
644 | #if DEBUG_DATASTORE | 644 | #if DEBUG_DATASTORE |
645 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | 645 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
646 | "Processing `%s' request\n", | 646 | "Processing `%s' request\n", |
647 | "RESERVE"); | 647 | "RESERVE"); |
648 | #endif | 648 | #endif |
649 | amount = ntohl(msg->amount); | 649 | amount = GNUNET_ntohll(msg->amount); |
650 | entries = GNUNET_ntohll(msg->entries); | 650 | entries = ntohl(msg->entries); |
651 | used = plugin->api->get_size (plugin->api->cls) + reserved; | 651 | used = plugin->api->get_size (plugin->api->cls) + reserved; |
652 | req = amount + ((unsigned long long) GNUNET_DATASTORE_ENTRY_OVERHEAD) * entries; | 652 | req = amount + ((unsigned long long) GNUNET_DATASTORE_ENTRY_OVERHEAD) * entries; |
653 | if (used + req > quota) | 653 | if (used + req > quota) |
diff --git a/src/datastore/plugin_datastore_sqlite.c b/src/datastore/plugin_datastore_sqlite.c index 9a807463a..af4dcc322 100644 --- a/src/datastore/plugin_datastore_sqlite.c +++ b/src/datastore/plugin_datastore_sqlite.c | |||
@@ -29,7 +29,7 @@ | |||
29 | #include "plugin_datastore.h" | 29 | #include "plugin_datastore.h" |
30 | #include <sqlite3.h> | 30 | #include <sqlite3.h> |
31 | 31 | ||
32 | #define DEBUG_SQLITE GNUNET_YES | 32 | #define DEBUG_SQLITE GNUNET_NO |
33 | 33 | ||
34 | /** | 34 | /** |
35 | * After how many payload-changing operations | 35 | * After how many payload-changing operations |
@@ -44,7 +44,7 @@ | |||
44 | * a failure of the command 'cmd' on file 'filename' | 44 | * a failure of the command 'cmd' on file 'filename' |
45 | * with the message given by strerror(errno). | 45 | * with the message given by strerror(errno). |
46 | */ | 46 | */ |
47 | #define LOG_SQLITE(db, msg, level, cmd) do { GNUNET_log_from (level, "sqlite", _("`%s' failed at %s:%d with error: %s\n"), cmd, __FILE__, __LINE__, sqlite3_errmsg(db->dbh)); if (msg != NULL) GNUNET_asprintf(msg, _("`%s' failed with error: %s\n"), cmd, sqlite3_errmsg(db->dbh)); } while(0) | 47 | #define LOG_SQLITE(db, msg, level, cmd) do { GNUNET_log_from (level, "sqlite", _("`%s' failed at %s:%d with error: %s\n"), cmd, __FILE__, __LINE__, sqlite3_errmsg(db->dbh)); if (msg != NULL) GNUNET_asprintf(msg, _("`%s' failed with error: %s"), cmd, sqlite3_errmsg(db->dbh)); } while(0) |
48 | 48 | ||
49 | #define SELECT_IT_LOW_PRIORITY_1 \ | 49 | #define SELECT_IT_LOW_PRIORITY_1 \ |
50 | "SELECT size,type,prio,anonLevel,expire,hash,value,_ROWID_ FROM gn080 WHERE (prio = ? AND hash > ?) "\ | 50 | "SELECT size,type,prio,anonLevel,expire,hash,value,_ROWID_ FROM gn080 WHERE (prio = ? AND hash > ?) "\ |
@@ -768,7 +768,7 @@ sqlite_plugin_update (void *cls, | |||
768 | sqlite3_bind_int64 (plugin->updPrio, 2, expire.value); | 768 | sqlite3_bind_int64 (plugin->updPrio, 2, expire.value); |
769 | sqlite3_bind_int64 (plugin->updPrio, 3, uid); | 769 | sqlite3_bind_int64 (plugin->updPrio, 3, uid); |
770 | n = sqlite3_step (plugin->updPrio); | 770 | n = sqlite3_step (plugin->updPrio); |
771 | if (n != SQLITE_OK) | 771 | if (n != SQLITE_DONE) |
772 | LOG_SQLITE (plugin, msg, | 772 | LOG_SQLITE (plugin, msg, |
773 | GNUNET_ERROR_TYPE_WARNING | GNUNET_ERROR_TYPE_BULK, | 773 | GNUNET_ERROR_TYPE_WARNING | GNUNET_ERROR_TYPE_BULK, |
774 | "sqlite3_step"); | 774 | "sqlite3_step"); |
@@ -782,7 +782,7 @@ sqlite_plugin_update (void *cls, | |||
782 | 782 | ||
783 | if (n == SQLITE_BUSY) | 783 | if (n == SQLITE_BUSY) |
784 | return GNUNET_NO; | 784 | return GNUNET_NO; |
785 | return n == SQLITE_OK ? GNUNET_OK : GNUNET_SYSERR; | 785 | return n == SQLITE_DONE ? GNUNET_OK : GNUNET_SYSERR; |
786 | } | 786 | } |
787 | 787 | ||
788 | 788 | ||
diff --git a/src/datastore/test_datastore_api.c b/src/datastore/test_datastore_api.c index 3d65bf813..005c11a58 100644 --- a/src/datastore/test_datastore_api.c +++ b/src/datastore/test_datastore_api.c | |||
@@ -19,13 +19,11 @@ | |||
19 | */ | 19 | */ |
20 | /* | 20 | /* |
21 | * @file datastore/test_datastore_api.c | 21 | * @file datastore/test_datastore_api.c |
22 | * @brief Test for the datastore implementation. | 22 | * @brief Test for the basic datastore API. |
23 | * @author Christian Grothoff | 23 | * @author Christian Grothoff |
24 | * | 24 | * |
25 | * TODO: | 25 | * TODO: |
26 | * - test multiple values under same key | 26 | * - test reservation failure |
27 | * - test "update" | ||
28 | * - test storage reservations | ||
29 | */ | 27 | */ |
30 | 28 | ||
31 | #include "platform.h" | 29 | #include "platform.h" |
@@ -91,7 +89,7 @@ get_expiration (int i) | |||
91 | { | 89 | { |
92 | struct GNUNET_TIME_Absolute av; | 90 | struct GNUNET_TIME_Absolute av; |
93 | 91 | ||
94 | av.value = now.value - i * 1000; | 92 | av.value = now.value + 200000 - i * 1000; |
95 | return av; | 93 | return av; |
96 | } | 94 | } |
97 | 95 | ||
@@ -102,7 +100,16 @@ enum RunPhase | |||
102 | RP_GET, | 100 | RP_GET, |
103 | RP_DEL, | 101 | RP_DEL, |
104 | RP_DO_DEL, | 102 | RP_DO_DEL, |
105 | RP_DELVALIDATE | 103 | RP_DELVALIDATE, |
104 | RP_RESERVE, | ||
105 | RP_PUT_MULTIPLE, | ||
106 | RP_PUT_MULTIPLE_NEXT, | ||
107 | RP_GET_MULTIPLE, | ||
108 | RP_GET_MULTIPLE_NEXT, | ||
109 | RP_GET_MULTIPLE_DONE, | ||
110 | RP_UPDATE, | ||
111 | RP_UPDATE_VALIDATE, | ||
112 | RP_UPDATE_DONE | ||
106 | }; | 113 | }; |
107 | 114 | ||
108 | 115 | ||
@@ -110,12 +117,14 @@ struct CpsRunContext | |||
110 | { | 117 | { |
111 | GNUNET_HashCode key; | 118 | GNUNET_HashCode key; |
112 | int i; | 119 | int i; |
120 | int rid; | ||
113 | int *iptr; | 121 | int *iptr; |
114 | struct GNUNET_SCHEDULER_Handle *sched; | 122 | struct GNUNET_SCHEDULER_Handle *sched; |
115 | struct GNUNET_CONFIGURATION_Handle *cfg; | 123 | struct GNUNET_CONFIGURATION_Handle *cfg; |
116 | void *data; | 124 | void *data; |
117 | size_t size; | 125 | size_t size; |
118 | enum RunPhase phase; | 126 | enum RunPhase phase; |
127 | unsigned long long uid; | ||
119 | }; | 128 | }; |
120 | 129 | ||
121 | 130 | ||
@@ -144,6 +153,25 @@ check_success (void *cls, | |||
144 | } | 153 | } |
145 | 154 | ||
146 | 155 | ||
156 | static void | ||
157 | get_reserved (void *cls, | ||
158 | int success, | ||
159 | const char *msg) | ||
160 | { | ||
161 | struct CpsRunContext *crc = cls; | ||
162 | if (0 >= success) | ||
163 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, | ||
164 | "%s\n", msg); | ||
165 | GNUNET_assert (0 < success); | ||
166 | crc->rid = success; | ||
167 | GNUNET_SCHEDULER_add_continuation (crc->sched, | ||
168 | GNUNET_NO, | ||
169 | &run_continuation, | ||
170 | crc, | ||
171 | GNUNET_SCHEDULER_REASON_PREREQ_DONE); | ||
172 | } | ||
173 | |||
174 | |||
147 | static void | 175 | static void |
148 | check_value (void *cls, | 176 | check_value (void *cls, |
149 | const GNUNET_HashCode * key, | 177 | const GNUNET_HashCode * key, |
@@ -227,7 +255,7 @@ check_nothing (void *cls, | |||
227 | GNUNET_assert (key == NULL); | 255 | GNUNET_assert (key == NULL); |
228 | if (crc->i == 0) | 256 | if (crc->i == 0) |
229 | { | 257 | { |
230 | crc->phase = RP_DONE; | 258 | crc->phase = RP_RESERVE; |
231 | } | 259 | } |
232 | GNUNET_SCHEDULER_add_continuation (crc->sched, | 260 | GNUNET_SCHEDULER_add_continuation (crc->sched, |
233 | GNUNET_NO, | 261 | GNUNET_NO, |
@@ -237,12 +265,81 @@ check_nothing (void *cls, | |||
237 | } | 265 | } |
238 | 266 | ||
239 | 267 | ||
268 | static void | ||
269 | check_multiple (void *cls, | ||
270 | const GNUNET_HashCode * key, | ||
271 | uint32_t size, | ||
272 | const void *data, | ||
273 | uint32_t type, | ||
274 | uint32_t priority, | ||
275 | uint32_t anonymity, | ||
276 | struct GNUNET_TIME_Absolute | ||
277 | expiration, uint64_t uid) | ||
278 | { | ||
279 | struct CpsRunContext *crc = cls; | ||
280 | |||
281 | if (key == NULL) | ||
282 | { | ||
283 | GNUNET_assert (crc->phase == RP_GET_MULTIPLE_DONE); | ||
284 | crc->phase = RP_UPDATE; | ||
285 | GNUNET_SCHEDULER_add_continuation (crc->sched, | ||
286 | GNUNET_NO, | ||
287 | &run_continuation, | ||
288 | crc, | ||
289 | GNUNET_SCHEDULER_REASON_PREREQ_DONE); | ||
290 | return; | ||
291 | } | ||
292 | crc->phase++; | ||
293 | if (priority == get_priority (42)) | ||
294 | crc->uid = uid; | ||
295 | } | ||
296 | |||
297 | |||
298 | static void | ||
299 | check_update (void *cls, | ||
300 | const GNUNET_HashCode * key, | ||
301 | uint32_t size, | ||
302 | const void *data, | ||
303 | uint32_t type, | ||
304 | uint32_t priority, | ||
305 | uint32_t anonymity, | ||
306 | struct GNUNET_TIME_Absolute | ||
307 | expiration, uint64_t uid) | ||
308 | { | ||
309 | struct CpsRunContext *crc = cls; | ||
310 | |||
311 | if (key == NULL) | ||
312 | { | ||
313 | GNUNET_assert (crc->phase == RP_UPDATE_DONE); | ||
314 | crc->phase = RP_DONE; | ||
315 | GNUNET_SCHEDULER_add_continuation (crc->sched, | ||
316 | GNUNET_NO, | ||
317 | &run_continuation, | ||
318 | crc, | ||
319 | GNUNET_SCHEDULER_REASON_PREREQ_DONE); | ||
320 | return; | ||
321 | } | ||
322 | if ( (anonymity == get_anonymity (42)) && | ||
323 | (size == get_size (42)) && | ||
324 | (priority == get_priority (42) + 100) ) | ||
325 | { | ||
326 | crc->phase = RP_UPDATE_DONE; | ||
327 | } | ||
328 | else | ||
329 | GNUNET_assert (size == get_size (43)); | ||
330 | } | ||
331 | |||
332 | |||
240 | static void | 333 | static void |
241 | run_continuation (void *cls, | 334 | run_continuation (void *cls, |
242 | const struct GNUNET_SCHEDULER_TaskContext *tc) | 335 | const struct GNUNET_SCHEDULER_TaskContext *tc) |
243 | { | 336 | { |
244 | struct CpsRunContext *crc = cls; | 337 | struct CpsRunContext *crc = cls; |
245 | ok = (int) crc->phase; | 338 | ok = (int) crc->phase; |
339 | #if VERBOSE | ||
340 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
341 | "Test in phase %u\n", crc->phase); | ||
342 | #endif | ||
246 | switch (crc->phase) | 343 | switch (crc->phase) |
247 | { | 344 | { |
248 | case RP_PUT: | 345 | case RP_PUT: |
@@ -341,9 +438,79 @@ run_continuation (void *cls, | |||
341 | crc, | 438 | crc, |
342 | TIMEOUT); | 439 | TIMEOUT); |
343 | break; | 440 | break; |
344 | /* check reservations */ | 441 | case RP_RESERVE: |
345 | /* check update */ | 442 | crc->phase = RP_PUT_MULTIPLE; |
346 | /* test multiple results */ | 443 | GNUNET_DATASTORE_reserve (datastore, |
444 | 128*1024, | ||
445 | 2, | ||
446 | &get_reserved, | ||
447 | crc, | ||
448 | TIMEOUT); | ||
449 | break; | ||
450 | case RP_PUT_MULTIPLE: | ||
451 | crc->phase = RP_PUT_MULTIPLE_NEXT; | ||
452 | GNUNET_DATASTORE_put (datastore, | ||
453 | crc->rid, | ||
454 | &crc->key, | ||
455 | get_size (42), | ||
456 | get_data (42), | ||
457 | get_type (42), | ||
458 | get_priority (42), | ||
459 | get_anonymity (42), | ||
460 | get_expiration (42), | ||
461 | TIMEOUT, | ||
462 | &check_success, | ||
463 | crc); | ||
464 | break; | ||
465 | case RP_PUT_MULTIPLE_NEXT: | ||
466 | crc->phase = RP_GET_MULTIPLE; | ||
467 | GNUNET_DATASTORE_put (datastore, | ||
468 | crc->rid, | ||
469 | &crc->key, | ||
470 | get_size (43), | ||
471 | get_data (43), | ||
472 | get_type (42), | ||
473 | get_priority (43), | ||
474 | get_anonymity (43), | ||
475 | get_expiration (43), | ||
476 | TIMEOUT, | ||
477 | &check_success, | ||
478 | crc); | ||
479 | break; | ||
480 | case RP_GET_MULTIPLE: | ||
481 | GNUNET_DATASTORE_get (datastore, | ||
482 | &crc->key, | ||
483 | get_type (42), | ||
484 | &check_multiple, | ||
485 | crc, | ||
486 | TIMEOUT); | ||
487 | break; | ||
488 | case RP_GET_MULTIPLE_NEXT: | ||
489 | case RP_GET_MULTIPLE_DONE: | ||
490 | GNUNET_assert (0); | ||
491 | break; | ||
492 | case RP_UPDATE: | ||
493 | GNUNET_assert (crc->uid > 0); | ||
494 | crc->phase = RP_UPDATE_VALIDATE; | ||
495 | GNUNET_DATASTORE_update (datastore, | ||
496 | crc->uid, | ||
497 | 100, | ||
498 | get_expiration (42), | ||
499 | &check_success, | ||
500 | crc, | ||
501 | TIMEOUT); | ||
502 | break; | ||
503 | case RP_UPDATE_VALIDATE: | ||
504 | GNUNET_DATASTORE_get (datastore, | ||
505 | &crc->key, | ||
506 | get_type (42), | ||
507 | &check_update, | ||
508 | crc, | ||
509 | TIMEOUT); | ||
510 | break; | ||
511 | case RP_UPDATE_DONE: | ||
512 | GNUNET_assert (0); | ||
513 | break; | ||
347 | case RP_DONE: | 514 | case RP_DONE: |
348 | #if VERBOSE | 515 | #if VERBOSE |
349 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | 516 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, |
@@ -368,7 +535,7 @@ run (void *cls, | |||
368 | crc->sched = sched; | 535 | crc->sched = sched; |
369 | crc->cfg = cfg; | 536 | crc->cfg = cfg; |
370 | crc->phase = RP_PUT; | 537 | crc->phase = RP_PUT; |
371 | now.value = 1000000; | 538 | now = GNUNET_TIME_absolute_get (); |
372 | datastore = GNUNET_DATASTORE_connect (cfg, sched); | 539 | datastore = GNUNET_DATASTORE_connect (cfg, sched); |
373 | GNUNET_SCHEDULER_add_continuation (crc->sched, | 540 | GNUNET_SCHEDULER_add_continuation (crc->sched, |
374 | GNUNET_NO, | 541 | GNUNET_NO, |
diff --git a/src/datastore/test_datastore_api_management.c b/src/datastore/test_datastore_api_management.c new file mode 100644 index 000000000..f5dfa8a07 --- /dev/null +++ b/src/datastore/test_datastore_api_management.c | |||
@@ -0,0 +1,377 @@ | |||
1 | /* | ||
2 | This file is part of GNUnet. | ||
3 | (C) 2004, 2005, 2006, 2007, 2009 Christian Grothoff (and other contributing authors) | ||
4 | |||
5 | GNUnet is free software; you can redistribute it and/or modify | ||
6 | it under the terms of the GNU General Public License as published | ||
7 | by the Free Software Foundation; either version 2, or (at your | ||
8 | 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 | General Public License for more details. | ||
14 | |||
15 | You should have received a copy of the GNU General Public License | ||
16 | along with GNUnet; see the file COPYING. If not, write to the | ||
17 | Free Software Foundation, Inc., 59 Temple Place - Suite 330, | ||
18 | Boston, MA 02111-1307, USA. | ||
19 | */ | ||
20 | /* | ||
21 | * @file datastore/test_datastore_api_management.c | ||
22 | * @brief Test for the space management functions of the datastore implementation. | ||
23 | * @author Christian Grothoff | ||
24 | */ | ||
25 | |||
26 | #include "platform.h" | ||
27 | #include "gnunet_util_lib.h" | ||
28 | #include "gnunet_protocols.h" | ||
29 | #include "gnunet_datastore_service.h" | ||
30 | |||
31 | #define VERBOSE GNUNET_NO | ||
32 | |||
33 | /** | ||
34 | * How long until we give up on transmitting the message? | ||
35 | */ | ||
36 | #define TIMEOUT GNUNET_TIME_relative_multiply (GNUNET_TIME_UNIT_SECONDS, 15) | ||
37 | |||
38 | /** | ||
39 | * Number of iterations to run; must be large enough | ||
40 | * so that the quota will be exceeded! | ||
41 | */ | ||
42 | #define ITERATIONS 5000 | ||
43 | |||
44 | static struct GNUNET_DATASTORE_Handle *datastore; | ||
45 | |||
46 | static struct GNUNET_TIME_Absolute now; | ||
47 | |||
48 | static int ok; | ||
49 | |||
50 | |||
51 | static size_t | ||
52 | get_size (int i) | ||
53 | { | ||
54 | return 8 + 8 * (i % 256); | ||
55 | } | ||
56 | |||
57 | |||
58 | static const void * | ||
59 | get_data (int i) | ||
60 | { | ||
61 | static char buf[60000]; | ||
62 | memset (buf, i, 8 + 8 * (i % 256)); | ||
63 | return buf; | ||
64 | } | ||
65 | |||
66 | |||
67 | static int | ||
68 | get_type(int i) | ||
69 | { | ||
70 | return 1; | ||
71 | } | ||
72 | |||
73 | |||
74 | static int | ||
75 | get_priority (int i) | ||
76 | { | ||
77 | return i+1; | ||
78 | } | ||
79 | |||
80 | |||
81 | static int | ||
82 | get_anonymity(int i) | ||
83 | { | ||
84 | return i; | ||
85 | } | ||
86 | |||
87 | |||
88 | static struct GNUNET_TIME_Absolute | ||
89 | get_expiration (int i) | ||
90 | { | ||
91 | struct GNUNET_TIME_Absolute av; | ||
92 | |||
93 | av.value = now.value + i * 1000; | ||
94 | return av; | ||
95 | } | ||
96 | |||
97 | enum RunPhase | ||
98 | { | ||
99 | RP_DONE = 0, | ||
100 | RP_PUT, | ||
101 | RP_GET, | ||
102 | RP_GET_FAIL | ||
103 | }; | ||
104 | |||
105 | |||
106 | struct CpsRunContext | ||
107 | { | ||
108 | GNUNET_HashCode key; | ||
109 | int i; | ||
110 | int found; | ||
111 | struct GNUNET_SCHEDULER_Handle *sched; | ||
112 | struct GNUNET_CONFIGURATION_Handle *cfg; | ||
113 | void *data; | ||
114 | size_t size; | ||
115 | enum RunPhase phase; | ||
116 | }; | ||
117 | |||
118 | |||
119 | static void | ||
120 | run_continuation (void *cls, | ||
121 | const struct GNUNET_SCHEDULER_TaskContext *tc); | ||
122 | |||
123 | |||
124 | static void | ||
125 | check_success (void *cls, | ||
126 | int success, | ||
127 | const char *msg) | ||
128 | { | ||
129 | struct CpsRunContext *crc = cls; | ||
130 | if (GNUNET_OK != success) | ||
131 | GNUNET_log (GNUNET_ERROR_TYPE_ERROR, | ||
132 | "%s\n", msg); | ||
133 | GNUNET_assert (GNUNET_OK == success); | ||
134 | GNUNET_free_non_null (crc->data); | ||
135 | crc->data = NULL; | ||
136 | GNUNET_SCHEDULER_add_continuation (crc->sched, | ||
137 | GNUNET_NO, | ||
138 | &run_continuation, | ||
139 | crc, | ||
140 | GNUNET_SCHEDULER_REASON_PREREQ_DONE); | ||
141 | } | ||
142 | |||
143 | |||
144 | static void | ||
145 | check_value (void *cls, | ||
146 | const GNUNET_HashCode * key, | ||
147 | uint32_t size, | ||
148 | const void *data, | ||
149 | uint32_t type, | ||
150 | uint32_t priority, | ||
151 | uint32_t anonymity, | ||
152 | struct GNUNET_TIME_Absolute | ||
153 | expiration, uint64_t uid) | ||
154 | { | ||
155 | struct CpsRunContext *crc = cls; | ||
156 | int i; | ||
157 | |||
158 | if (key == NULL) | ||
159 | { | ||
160 | crc->i--; | ||
161 | if (crc->found == GNUNET_YES) | ||
162 | { | ||
163 | crc->phase = RP_GET; | ||
164 | crc->found = GNUNET_NO; | ||
165 | } | ||
166 | else | ||
167 | { | ||
168 | fprintf (stderr, | ||
169 | "First not found was %u\n", crc->i); | ||
170 | crc->phase = RP_GET_FAIL; | ||
171 | } | ||
172 | if (0 == crc->i) | ||
173 | crc->phase = RP_DONE; | ||
174 | GNUNET_SCHEDULER_add_continuation (crc->sched, | ||
175 | GNUNET_NO, | ||
176 | &run_continuation, | ||
177 | crc, | ||
178 | GNUNET_SCHEDULER_REASON_PREREQ_DONE); | ||
179 | return; | ||
180 | } | ||
181 | i = crc->i; | ||
182 | crc->found = GNUNET_YES; | ||
183 | GNUNET_assert (size == get_size (i)); | ||
184 | GNUNET_assert (0 == memcmp (data, get_data(i), size)); | ||
185 | GNUNET_assert (type == get_type (i)); | ||
186 | GNUNET_assert (priority == get_priority (i)); | ||
187 | GNUNET_assert (anonymity == get_anonymity(i)); | ||
188 | GNUNET_assert (expiration.value == get_expiration(i).value); | ||
189 | } | ||
190 | |||
191 | |||
192 | static void | ||
193 | check_nothing (void *cls, | ||
194 | const GNUNET_HashCode * key, | ||
195 | uint32_t size, | ||
196 | const void *data, | ||
197 | uint32_t type, | ||
198 | uint32_t priority, | ||
199 | uint32_t anonymity, | ||
200 | struct GNUNET_TIME_Absolute | ||
201 | expiration, uint64_t uid) | ||
202 | { | ||
203 | struct CpsRunContext *crc = cls; | ||
204 | GNUNET_assert (key == NULL); | ||
205 | if (crc->i == 0) | ||
206 | { | ||
207 | crc->phase = RP_DONE; | ||
208 | } | ||
209 | GNUNET_SCHEDULER_add_continuation (crc->sched, | ||
210 | GNUNET_NO, | ||
211 | &run_continuation, | ||
212 | crc, | ||
213 | GNUNET_SCHEDULER_REASON_PREREQ_DONE); | ||
214 | } | ||
215 | |||
216 | |||
217 | static void | ||
218 | run_continuation (void *cls, | ||
219 | const struct GNUNET_SCHEDULER_TaskContext *tc) | ||
220 | { | ||
221 | struct CpsRunContext *crc = cls; | ||
222 | ok = (int) crc->phase; | ||
223 | switch (crc->phase) | ||
224 | { | ||
225 | case RP_PUT: | ||
226 | #if VERBOSE | ||
227 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
228 | "Executing `%s' number %u\n", | ||
229 | "PUT", | ||
230 | crc->i); | ||
231 | #endif | ||
232 | GNUNET_CRYPTO_hash (&crc->i, sizeof (int), &crc->key); | ||
233 | GNUNET_DATASTORE_put (datastore, | ||
234 | 0, | ||
235 | &crc->key, | ||
236 | get_size (crc->i), | ||
237 | get_data (crc->i), | ||
238 | get_type (crc->i), | ||
239 | get_priority (crc->i), | ||
240 | get_anonymity (crc->i), | ||
241 | get_expiration (crc->i), | ||
242 | TIMEOUT, | ||
243 | &check_success, | ||
244 | crc); | ||
245 | crc->i++; | ||
246 | if (crc->i == ITERATIONS) | ||
247 | { | ||
248 | GNUNET_log (GNUNET_ERROR_TYPE_INFO, | ||
249 | "Sleeping to give datastore time to clean up\n"); | ||
250 | sleep (5); | ||
251 | crc->phase = RP_GET; | ||
252 | crc->i--; | ||
253 | } | ||
254 | break; | ||
255 | case RP_GET: | ||
256 | #if VERBOSE | ||
257 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
258 | "Executing `%s' number %u\n", | ||
259 | "GET", | ||
260 | crc->i); | ||
261 | #endif | ||
262 | GNUNET_CRYPTO_hash (&crc->i, sizeof (int), &crc->key); | ||
263 | GNUNET_DATASTORE_get (datastore, | ||
264 | &crc->key, | ||
265 | get_type (crc->i), | ||
266 | &check_value, | ||
267 | crc, | ||
268 | TIMEOUT); | ||
269 | break; | ||
270 | case RP_GET_FAIL: | ||
271 | #if VERBOSE | ||
272 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
273 | "Executing `%s' number %u\n", | ||
274 | "GET", | ||
275 | crc->i); | ||
276 | #endif | ||
277 | GNUNET_CRYPTO_hash (&crc->i, sizeof (int), &crc->key); | ||
278 | GNUNET_DATASTORE_get (datastore, | ||
279 | &crc->key, | ||
280 | get_type (crc->i), | ||
281 | &check_nothing, | ||
282 | crc, | ||
283 | TIMEOUT); | ||
284 | break; | ||
285 | case RP_DONE: | ||
286 | #if VERBOSE | ||
287 | GNUNET_log (GNUNET_ERROR_TYPE_DEBUG, | ||
288 | "Finished, disconnecting\n"); | ||
289 | #endif | ||
290 | GNUNET_DATASTORE_disconnect (datastore, GNUNET_YES); | ||
291 | GNUNET_free (crc); | ||
292 | ok = 0; | ||
293 | } | ||
294 | } | ||
295 | |||
296 | |||
297 | static void | ||
298 | run (void *cls, | ||
299 | struct GNUNET_SCHEDULER_Handle *sched, | ||
300 | char *const *args, | ||
301 | const char *cfgfile, struct GNUNET_CONFIGURATION_Handle *cfg) | ||
302 | { | ||
303 | struct CpsRunContext *crc; | ||
304 | |||
305 | crc = GNUNET_malloc(sizeof(struct CpsRunContext)); | ||
306 | crc->sched = sched; | ||
307 | crc->cfg = cfg; | ||
308 | crc->phase = RP_PUT; | ||
309 | now = GNUNET_TIME_absolute_get (); | ||
310 | datastore = GNUNET_DATASTORE_connect (cfg, sched); | ||
311 | GNUNET_SCHEDULER_add_continuation (crc->sched, | ||
312 | GNUNET_NO, | ||
313 | &run_continuation, | ||
314 | crc, | ||
315 | GNUNET_SCHEDULER_REASON_PREREQ_DONE); | ||
316 | |||
317 | } | ||
318 | |||
319 | |||
320 | |||
321 | static int | ||
322 | check () | ||
323 | { | ||
324 | pid_t pid; | ||
325 | char *const argv[] = { "test-datastore-api-management", | ||
326 | "-c", | ||
327 | "test_datastore_api_data.conf", | ||
328 | #if VERBOSE | ||
329 | "-L", "DEBUG", | ||
330 | #endif | ||
331 | NULL | ||
332 | }; | ||
333 | struct GNUNET_GETOPT_CommandLineOption options[] = { | ||
334 | GNUNET_GETOPT_OPTION_END | ||
335 | }; | ||
336 | pid = GNUNET_OS_start_process ("gnunet-service-datastore", | ||
337 | "gnunet-service-datastore", | ||
338 | #if VERBOSE | ||
339 | "-L", "DEBUG", | ||
340 | #endif | ||
341 | "-c", "test_datastore_api_data.conf", NULL); | ||
342 | sleep (1); | ||
343 | GNUNET_PROGRAM_run ((sizeof (argv) / sizeof (char *)) - 1, | ||
344 | argv, "test-datastore-api", "nohelp", | ||
345 | options, &run, NULL); | ||
346 | if (0 != PLIBC_KILL (pid, SIGTERM)) | ||
347 | { | ||
348 | GNUNET_log_strerror (GNUNET_ERROR_TYPE_WARNING, "kill"); | ||
349 | ok = 1; | ||
350 | } | ||
351 | GNUNET_OS_process_wait(pid); | ||
352 | if (ok != 0) | ||
353 | fprintf (stderr, "Missed some testcases: %u\n", ok); | ||
354 | return ok; | ||
355 | } | ||
356 | |||
357 | int | ||
358 | main (int argc, char *argv[]) | ||
359 | { | ||
360 | int ret; | ||
361 | |||
362 | GNUNET_DISK_directory_remove ("/tmp/test-gnunetd-datastore"); | ||
363 | GNUNET_log_setup ("test-datastore-api", | ||
364 | #if VERBOSE | ||
365 | "DEBUG", | ||
366 | #else | ||
367 | "WARNING", | ||
368 | #endif | ||
369 | NULL); | ||
370 | ret = check (); | ||
371 | |||
372 | return ret; | ||
373 | } | ||
374 | |||
375 | |||
376 | |||
377 | /* end of test_datastore_api_management.c */ | ||