Merging replication
[m6w6/libmemcached] / tests / function.c
1 /*
2 Sample test application.
3 */
4 #include "libmemcached/common.h"
5
6 #include <assert.h>
7 #include <stdio.h>
8 #include <stdlib.h>
9 #include <string.h>
10 #include <sys/time.h>
11 #include <sys/types.h>
12 #include <sys/stat.h>
13 #include <unistd.h>
14 #include <time.h>
15 #include "server.h"
16 #include "clients/generator.h"
17 #include "clients/execute.h"
18
19 #ifndef INT64_MAX
20 #define INT64_MAX LONG_MAX
21 #endif
22 #ifndef INT32_MAX
23 #define INT32_MAX INT_MAX
24 #endif
25
26
27 #include "test.h"
28
29 #ifdef HAVE_LIBMEMCACHEDUTIL
30 #include <pthread.h>
31 #include "libmemcached/memcached_util.h"
32 #endif
33
34 #define GLOBAL_COUNT 10000
35 #define GLOBAL2_COUNT 100
36 #define SERVERS_TO_CREATE 5
37 static uint32_t global_count;
38
39 static pairs_st *global_pairs;
40 static char *global_keys[GLOBAL_COUNT];
41 static size_t global_keys_length[GLOBAL_COUNT];
42
43 static test_return init_test(memcached_st *not_used __attribute__((unused)))
44 {
45 memcached_st memc;
46
47 (void)memcached_create(&memc);
48 memcached_free(&memc);
49
50 return 0;
51 }
52
53 static test_return server_list_null_test(memcached_st *ptr __attribute__((unused)))
54 {
55 memcached_server_st *server_list;
56 memcached_return rc;
57
58 server_list= memcached_server_list_append_with_weight(NULL, NULL, 0, 0, NULL);
59 assert(server_list == NULL);
60
61 server_list= memcached_server_list_append_with_weight(NULL, "localhost", 0, 0, NULL);
62 assert(server_list == NULL);
63
64 server_list= memcached_server_list_append_with_weight(NULL, NULL, 0, 0, &rc);
65 assert(server_list == NULL);
66
67 return 0;
68 }
69
70 #define TEST_PORT_COUNT 7
71 uint32_t test_ports[TEST_PORT_COUNT];
72
73 static memcached_return server_display_function(memcached_st *ptr __attribute__((unused)), memcached_server_st *server, void *context)
74 {
75 /* Do Nothing */
76 uint32_t bigger= *((uint32_t *)(context));
77 assert(bigger <= server->port);
78 *((uint32_t *)(context))= server->port;
79
80 return MEMCACHED_SUCCESS;
81 }
82
83 static test_return server_sort_test(memcached_st *ptr __attribute__((unused)))
84 {
85 uint32_t x;
86 uint32_t bigger= 0; /* Prime the value for the assert in server_display_function */
87 memcached_return rc;
88 memcached_server_function callbacks[1];
89 memcached_st *local_memc;
90
91 local_memc= memcached_create(NULL);
92 assert(local_memc);
93 memcached_behavior_set(local_memc, MEMCACHED_BEHAVIOR_SORT_HOSTS, 1);
94
95 for (x= 0; x < TEST_PORT_COUNT; x++)
96 {
97 test_ports[x]= random() % 64000;
98 rc= memcached_server_add_with_weight(local_memc, "localhost", test_ports[x], 0);
99 assert(local_memc->number_of_hosts == x + 1);
100 assert(local_memc->hosts[0].count == x+1);
101 assert(rc == MEMCACHED_SUCCESS);
102 }
103
104 callbacks[0]= server_display_function;
105 memcached_server_cursor(local_memc, callbacks, (void *)&bigger, 1);
106
107
108 memcached_free(local_memc);
109
110 return 0;
111 }
112
113 static test_return server_sort2_test(memcached_st *ptr __attribute__((unused)))
114 {
115 uint32_t bigger= 0; /* Prime the value for the assert in server_display_function */
116 memcached_return rc;
117 memcached_server_function callbacks[1];
118 memcached_st *local_memc;
119
120 local_memc= memcached_create(NULL);
121 assert(local_memc);
122 rc= memcached_behavior_set(local_memc, MEMCACHED_BEHAVIOR_SORT_HOSTS, 1);
123 assert(rc == MEMCACHED_SUCCESS);
124
125 rc= memcached_server_add_with_weight(local_memc, "MEMCACHED_BEHAVIOR_SORT_HOSTS", 43043, 0);
126 assert(rc == MEMCACHED_SUCCESS);
127 assert(local_memc->hosts[0].port == 43043);
128
129 rc= memcached_server_add_with_weight(local_memc, "MEMCACHED_BEHAVIOR_SORT_HOSTS", 43042, 0);
130 assert(rc == MEMCACHED_SUCCESS);
131 assert(local_memc->hosts[0].port == 43042);
132 assert(local_memc->hosts[1].port == 43043);
133
134 callbacks[0]= server_display_function;
135 memcached_server_cursor(local_memc, callbacks, (void *)&bigger, 1);
136
137
138 memcached_free(local_memc);
139
140 return 0;
141 }
142
143 static memcached_return server_display_unsort_function(memcached_st *ptr __attribute__((unused)), memcached_server_st *server, void *context)
144 {
145 /* Do Nothing */
146 uint32_t x= *((uint32_t *)(context));
147
148 assert(test_ports[x] == server->port);
149 *((uint32_t *)(context))= ++x;
150
151 return MEMCACHED_SUCCESS;
152 }
153
154 static test_return server_unsort_test(memcached_st *ptr __attribute__((unused)))
155 {
156 uint32_t x;
157 uint32_t counter= 0; /* Prime the value for the assert in server_display_function */
158 uint32_t bigger= 0; /* Prime the value for the assert in server_display_function */
159 memcached_return rc;
160 memcached_server_function callbacks[1];
161 memcached_st *local_memc;
162
163 local_memc= memcached_create(NULL);
164 assert(local_memc);
165
166 for (x= 0; x < TEST_PORT_COUNT; x++)
167 {
168 test_ports[x]= random() % 64000;
169 rc= memcached_server_add_with_weight(local_memc, "localhost", test_ports[x], 0);
170 assert(local_memc->number_of_hosts == x+1);
171 assert(local_memc->hosts[0].count == x+1);
172 assert(rc == MEMCACHED_SUCCESS);
173 }
174
175 callbacks[0]= server_display_unsort_function;
176 memcached_server_cursor(local_memc, callbacks, (void *)&counter, 1);
177
178 /* Now we sort old data! */
179 memcached_behavior_set(local_memc, MEMCACHED_BEHAVIOR_SORT_HOSTS, 1);
180 callbacks[0]= server_display_function;
181 memcached_server_cursor(local_memc, callbacks, (void *)&bigger, 1);
182
183
184 memcached_free(local_memc);
185
186 return 0;
187 }
188
189 static test_return allocation_test(memcached_st *not_used __attribute__((unused)))
190 {
191 memcached_st *memc;
192 memc= memcached_create(NULL);
193 assert(memc);
194 memcached_free(memc);
195
196 return 0;
197 }
198
199 static test_return clone_test(memcached_st *memc)
200 {
201 /* All null? */
202 {
203 memcached_st *clone;
204 clone= memcached_clone(NULL, NULL);
205 assert(clone);
206 memcached_free(clone);
207 }
208
209 /* Can we init from null? */
210 {
211 memcached_st *clone;
212 clone= memcached_clone(NULL, memc);
213 assert(clone);
214
215 assert(clone->call_free == memc->call_free);
216 assert(clone->call_malloc == memc->call_malloc);
217 assert(clone->call_realloc == memc->call_realloc);
218 assert(clone->call_calloc == memc->call_calloc);
219 assert(clone->connect_timeout == memc->connect_timeout);
220 assert(clone->delete_trigger == memc->delete_trigger);
221 assert(clone->distribution == memc->distribution);
222 assert(clone->flags == memc->flags);
223 assert(clone->get_key_failure == memc->get_key_failure);
224 assert(clone->hash == memc->hash);
225 assert(clone->hash_continuum == memc->hash_continuum);
226 assert(clone->io_bytes_watermark == memc->io_bytes_watermark);
227 assert(clone->io_msg_watermark == memc->io_msg_watermark);
228 assert(clone->io_key_prefetch == memc->io_key_prefetch);
229 assert(clone->on_cleanup == memc->on_cleanup);
230 assert(clone->on_clone == memc->on_clone);
231 assert(clone->poll_timeout == memc->poll_timeout);
232 assert(clone->rcv_timeout == memc->rcv_timeout);
233 assert(clone->recv_size == memc->recv_size);
234 assert(clone->retry_timeout == memc->retry_timeout);
235 assert(clone->send_size == memc->send_size);
236 assert(clone->server_failure_limit == memc->server_failure_limit);
237 assert(clone->snd_timeout == memc->snd_timeout);
238 assert(clone->user_data == memc->user_data);
239 assert(clone->number_of_replicas == memc->number_of_replicas);
240
241 memcached_free(clone);
242 }
243
244 /* Can we init from struct? */
245 {
246 memcached_st declared_clone;
247 memcached_st *clone;
248 memset(&declared_clone, 0 , sizeof(memcached_st));
249 clone= memcached_clone(&declared_clone, NULL);
250 assert(clone);
251 memcached_free(clone);
252 }
253
254 /* Can we init from struct? */
255 {
256 memcached_st declared_clone;
257 memcached_st *clone;
258 memset(&declared_clone, 0 , sizeof(memcached_st));
259 clone= memcached_clone(&declared_clone, memc);
260 assert(clone);
261 memcached_free(clone);
262 }
263
264 return 0;
265 }
266
267 static test_return userdata_test(memcached_st *memc)
268 {
269 void* foo;
270 assert(memcached_set_user_data(memc, foo) == NULL);
271 assert(memcached_get_user_data(memc) == foo);
272 assert(memcached_set_user_data(memc, NULL) == foo);
273
274 return TEST_SUCCESS;
275 }
276
277 static test_return connection_test(memcached_st *memc)
278 {
279 memcached_return rc;
280
281 rc= memcached_server_add_with_weight(memc, "localhost", 0, 0);
282 assert(rc == MEMCACHED_SUCCESS);
283
284 return 0;
285 }
286
287 static test_return error_test(memcached_st *memc)
288 {
289 memcached_return rc;
290
291 for (rc= MEMCACHED_SUCCESS; rc < MEMCACHED_MAXIMUM_RETURN; rc++)
292 {
293 printf("Error %d -> %s\n", rc, memcached_strerror(memc, rc));
294 }
295
296 return 0;
297 }
298
299 static test_return set_test(memcached_st *memc)
300 {
301 memcached_return rc;
302 char *key= "foo";
303 char *value= "when we sanitize";
304
305 rc= memcached_set(memc, key, strlen(key),
306 value, strlen(value),
307 (time_t)0, (uint32_t)0);
308 assert(rc == MEMCACHED_SUCCESS || rc == MEMCACHED_BUFFERED);
309
310 return 0;
311 }
312
313 static test_return append_test(memcached_st *memc)
314 {
315 memcached_return rc;
316 char *key= "fig";
317 char *value= "we";
318 size_t value_length;
319 uint32_t flags;
320
321 rc= memcached_flush(memc, 0);
322 assert(rc == MEMCACHED_SUCCESS);
323
324 rc= memcached_set(memc, key, strlen(key),
325 value, strlen(value),
326 (time_t)0, (uint32_t)0);
327 assert(rc == MEMCACHED_SUCCESS);
328
329 rc= memcached_append(memc, key, strlen(key),
330 " the", strlen(" the"),
331 (time_t)0, (uint32_t)0);
332 assert(rc == MEMCACHED_SUCCESS);
333
334 rc= memcached_append(memc, key, strlen(key),
335 " people", strlen(" people"),
336 (time_t)0, (uint32_t)0);
337 assert(rc == MEMCACHED_SUCCESS);
338
339 value= memcached_get(memc, key, strlen(key),
340 &value_length, &flags, &rc);
341 assert(!memcmp(value, "we the people", strlen("we the people")));
342 assert(strlen("we the people") == value_length);
343 assert(rc == MEMCACHED_SUCCESS);
344 free(value);
345
346 return 0;
347 }
348
349 static test_return append_binary_test(memcached_st *memc)
350 {
351 memcached_return rc;
352 char *key= "numbers";
353 unsigned int *store_ptr;
354 unsigned int store_list[] = { 23, 56, 499, 98, 32847, 0 };
355 char *value;
356 size_t value_length;
357 uint32_t flags;
358 unsigned int x;
359
360 rc= memcached_flush(memc, 0);
361 assert(rc == MEMCACHED_SUCCESS);
362
363 rc= memcached_set(memc,
364 key, strlen(key),
365 NULL, 0,
366 (time_t)0, (uint32_t)0);
367 assert(rc == MEMCACHED_SUCCESS);
368
369 for (x= 0; store_list[x] ; x++)
370 {
371 rc= memcached_append(memc,
372 key, strlen(key),
373 (char *)&store_list[x], sizeof(unsigned int),
374 (time_t)0, (uint32_t)0);
375 assert(rc == MEMCACHED_SUCCESS);
376 }
377
378 value= memcached_get(memc, key, strlen(key),
379 &value_length, &flags, &rc);
380 assert((value_length == (sizeof(unsigned int) * x)));
381 assert(rc == MEMCACHED_SUCCESS);
382
383 store_ptr= (unsigned int *)value;
384 x= 0;
385 while ((size_t)store_ptr < (size_t)(value + value_length))
386 {
387 assert(*store_ptr == store_list[x++]);
388 store_ptr++;
389 }
390 free(value);
391
392 return 0;
393 }
394
395 static test_return cas2_test(memcached_st *memc)
396 {
397 memcached_return rc;
398 char *keys[]= {"fudge", "son", "food"};
399 size_t key_length[]= {5, 3, 4};
400 char *value= "we the people";
401 size_t value_length= strlen("we the people");
402 unsigned int x;
403 memcached_result_st results_obj;
404 memcached_result_st *results;
405 unsigned int set= 1;
406
407 rc= memcached_flush(memc, 0);
408 assert(rc == MEMCACHED_SUCCESS);
409
410 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_SUPPORT_CAS, set);
411
412 for (x= 0; x < 3; x++)
413 {
414 rc= memcached_set(memc, keys[x], key_length[x],
415 keys[x], key_length[x],
416 (time_t)50, (uint32_t)9);
417 assert(rc == MEMCACHED_SUCCESS);
418 }
419
420 rc= memcached_mget(memc, keys, key_length, 3);
421
422 results= memcached_result_create(memc, &results_obj);
423
424 results= memcached_fetch_result(memc, &results_obj, &rc);
425 assert(results);
426 assert(results->cas);
427 assert(rc == MEMCACHED_SUCCESS);
428 WATCHPOINT_ASSERT(memcached_result_cas(results));
429
430 assert(!memcmp(value, "we the people", strlen("we the people")));
431 assert(strlen("we the people") == value_length);
432 assert(rc == MEMCACHED_SUCCESS);
433
434 memcached_result_free(&results_obj);
435
436 return 0;
437 }
438
439 static test_return cas_test(memcached_st *memc)
440 {
441 memcached_return rc;
442 const char *key= "fun";
443 size_t key_length= strlen(key);
444 const char *value= "we the people";
445 char* keys[2] = { (char*)key, NULL };
446 size_t keylengths[2] = { strlen(key), 0 };
447 size_t value_length= strlen(value);
448 const char *value2= "change the value";
449 size_t value2_length= strlen(value2);
450
451 memcached_result_st results_obj;
452 memcached_result_st *results;
453 unsigned int set= 1;
454
455 rc= memcached_flush(memc, 0);
456 assert(rc == MEMCACHED_SUCCESS);
457
458 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_SUPPORT_CAS, set);
459
460 rc= memcached_set(memc, key, strlen(key),
461 value, strlen(value),
462 (time_t)0, (uint32_t)0);
463 assert(rc == MEMCACHED_SUCCESS);
464
465 rc= memcached_mget(memc, keys, keylengths, 1);
466
467 results= memcached_result_create(memc, &results_obj);
468
469 results= memcached_fetch_result(memc, &results_obj, &rc);
470 assert(results);
471 assert(rc == MEMCACHED_SUCCESS);
472 WATCHPOINT_ASSERT(memcached_result_cas(results));
473 assert(!memcmp(value, memcached_result_value(results), value_length));
474 assert(strlen(memcached_result_value(results)) == value_length);
475 assert(rc == MEMCACHED_SUCCESS);
476 uint64_t cas = memcached_result_cas(results);
477
478 #if 0
479 results= memcached_fetch_result(memc, &results_obj, &rc);
480 assert(rc == MEMCACHED_END);
481 assert(results == NULL);
482 #endif
483
484 rc= memcached_cas(memc, key, key_length, value2, value2_length, 0, 0, cas);
485 assert(rc == MEMCACHED_SUCCESS);
486
487 /*
488 * The item will have a new cas value, so try to set it again with the old
489 * value. This should fail!
490 */
491 rc= memcached_cas(memc, key, key_length, value2, value2_length, 0, 0, cas);
492 assert(rc == MEMCACHED_DATA_EXISTS);
493
494 memcached_result_free(&results_obj);
495
496 return 0;
497 }
498
499 static test_return prepend_test(memcached_st *memc)
500 {
501 memcached_return rc;
502 char *key= "fig";
503 char *value= "people";
504 size_t value_length;
505 uint32_t flags;
506
507 rc= memcached_flush(memc, 0);
508 assert(rc == MEMCACHED_SUCCESS);
509
510 rc= memcached_set(memc, key, strlen(key),
511 value, strlen(value),
512 (time_t)0, (uint32_t)0);
513 assert(rc == MEMCACHED_SUCCESS);
514
515 rc= memcached_prepend(memc, key, strlen(key),
516 "the ", strlen("the "),
517 (time_t)0, (uint32_t)0);
518 assert(rc == MEMCACHED_SUCCESS);
519
520 rc= memcached_prepend(memc, key, strlen(key),
521 "we ", strlen("we "),
522 (time_t)0, (uint32_t)0);
523 assert(rc == MEMCACHED_SUCCESS);
524
525 value= memcached_get(memc, key, strlen(key),
526 &value_length, &flags, &rc);
527 assert(!memcmp(value, "we the people", strlen("we the people")));
528 assert(strlen("we the people") == value_length);
529 assert(rc == MEMCACHED_SUCCESS);
530 free(value);
531
532 return 0;
533 }
534
535 /*
536 Set the value, then quit to make sure it is flushed.
537 Come back in and test that add fails.
538 */
539 static test_return add_test(memcached_st *memc)
540 {
541 memcached_return rc;
542 char *key= "foo";
543 char *value= "when we sanitize";
544 unsigned long long setting_value;
545
546 setting_value= memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_NO_BLOCK);
547
548 rc= memcached_set(memc, key, strlen(key),
549 value, strlen(value),
550 (time_t)0, (uint32_t)0);
551 assert(rc == MEMCACHED_SUCCESS || rc == MEMCACHED_BUFFERED);
552 memcached_quit(memc);
553 rc= memcached_add(memc, key, strlen(key),
554 value, strlen(value),
555 (time_t)0, (uint32_t)0);
556
557 /* Too many broken OS'es have broken loopback in async, so we can't be sure of the result */
558 if (setting_value)
559 assert(rc == MEMCACHED_NOTSTORED || rc == MEMCACHED_STORED);
560 else
561 assert(rc == MEMCACHED_NOTSTORED || rc == MEMCACHED_DATA_EXISTS);
562
563 return 0;
564 }
565
566 /*
567 ** There was a problem of leaking filedescriptors in the initial release
568 ** of MacOSX 10.5. This test case triggers the problem. On some Solaris
569 ** systems it seems that the kernel is slow on reclaiming the resources
570 ** because the connects starts to time out (the test doesn't do much
571 ** anyway, so just loop 10 iterations)
572 */
573 static test_return add_wrapper(memcached_st *memc)
574 {
575 unsigned int x;
576 unsigned int max= 10000;
577 #ifdef __sun
578 max= 10;
579 #endif
580
581 for (x= 0; x < max; x++)
582 add_test(memc);
583
584 return 0;
585 }
586
587 static test_return replace_test(memcached_st *memc)
588 {
589 memcached_return rc;
590 char *key= "foo";
591 char *value= "when we sanitize";
592 char *original= "first we insert some data";
593
594 rc= memcached_set(memc, key, strlen(key),
595 original, strlen(original),
596 (time_t)0, (uint32_t)0);
597 assert(rc == MEMCACHED_SUCCESS || rc == MEMCACHED_BUFFERED);
598
599 rc= memcached_replace(memc, key, strlen(key),
600 value, strlen(value),
601 (time_t)0, (uint32_t)0);
602 assert(rc == MEMCACHED_SUCCESS);
603
604 return 0;
605 }
606
607 static test_return delete_test(memcached_st *memc)
608 {
609 memcached_return rc;
610 char *key= "foo";
611 char *value= "when we sanitize";
612
613 rc= memcached_set(memc, key, strlen(key),
614 value, strlen(value),
615 (time_t)0, (uint32_t)0);
616 assert(rc == MEMCACHED_SUCCESS || rc == MEMCACHED_BUFFERED);
617
618 rc= memcached_delete(memc, key, strlen(key), (time_t)0);
619 assert(rc == MEMCACHED_SUCCESS || rc == MEMCACHED_BUFFERED);
620
621 return 0;
622 }
623
624 static test_return flush_test(memcached_st *memc)
625 {
626 memcached_return rc;
627
628 rc= memcached_flush(memc, 0);
629 assert(rc == MEMCACHED_SUCCESS);
630
631 return 0;
632 }
633
634 static memcached_return server_function(memcached_st *ptr __attribute__((unused)),
635 memcached_server_st *server __attribute__((unused)),
636 void *context __attribute__((unused)))
637 {
638 /* Do Nothing */
639
640 return MEMCACHED_SUCCESS;
641 }
642
643 static test_return memcached_server_cursor_test(memcached_st *memc)
644 {
645 char *context= "foo bad";
646 memcached_server_function callbacks[1];
647
648 callbacks[0]= server_function;
649 memcached_server_cursor(memc, callbacks, context, 1);
650
651 return 0;
652 }
653
654 static test_return bad_key_test(memcached_st *memc)
655 {
656 memcached_return rc;
657 char *key= "foo bad";
658 char *string;
659 size_t string_length;
660 uint32_t flags;
661 memcached_st *clone;
662 unsigned int set= 1;
663 size_t max_keylen= 0xffff;
664
665 clone= memcached_clone(NULL, memc);
666 assert(clone);
667
668 rc= memcached_behavior_set(clone, MEMCACHED_BEHAVIOR_VERIFY_KEY, set);
669 assert(rc == MEMCACHED_SUCCESS);
670
671 /* All keys are valid in the binary protocol (except for length) */
672 if (memcached_behavior_get(clone, MEMCACHED_BEHAVIOR_BINARY_PROTOCOL) == 0)
673 {
674 string= memcached_get(clone, key, strlen(key),
675 &string_length, &flags, &rc);
676 assert(rc == MEMCACHED_BAD_KEY_PROVIDED);
677 assert(string_length == 0);
678 assert(!string);
679
680 set= 0;
681 rc= memcached_behavior_set(clone, MEMCACHED_BEHAVIOR_VERIFY_KEY, set);
682 assert(rc == MEMCACHED_SUCCESS);
683 string= memcached_get(clone, key, strlen(key),
684 &string_length, &flags, &rc);
685 assert(rc == MEMCACHED_NOTFOUND);
686 assert(string_length == 0);
687 assert(!string);
688
689 /* Test multi key for bad keys */
690 char *keys[] = { "GoodKey", "Bad Key", "NotMine" };
691 size_t key_lengths[] = { 7, 7, 7 };
692 set= 1;
693 rc= memcached_behavior_set(clone, MEMCACHED_BEHAVIOR_VERIFY_KEY, set);
694 assert(rc == MEMCACHED_SUCCESS);
695
696 rc= memcached_mget(clone, keys, key_lengths, 3);
697 assert(rc == MEMCACHED_BAD_KEY_PROVIDED);
698
699 rc= memcached_mget_by_key(clone, "foo daddy", 9, keys, key_lengths, 1);
700 assert(rc == MEMCACHED_BAD_KEY_PROVIDED);
701
702 max_keylen= 250;
703
704 /* The following test should be moved to the end of this function when the
705 memcached server is updated to allow max size length of the keys in the
706 binary protocol
707 */
708 rc= memcached_callback_set(clone, MEMCACHED_CALLBACK_PREFIX_KEY, NULL);
709 assert(rc == MEMCACHED_SUCCESS);
710
711 char *longkey= malloc(max_keylen + 1);
712 if (longkey != NULL)
713 {
714 memset(longkey, 'a', max_keylen + 1);
715 string= memcached_get(clone, longkey, max_keylen,
716 &string_length, &flags, &rc);
717 assert(rc == MEMCACHED_NOTFOUND);
718 assert(string_length == 0);
719 assert(!string);
720
721 string= memcached_get(clone, longkey, max_keylen + 1,
722 &string_length, &flags, &rc);
723 assert(rc == MEMCACHED_BAD_KEY_PROVIDED);
724 assert(string_length == 0);
725 assert(!string);
726
727 free(longkey);
728 }
729 }
730
731 /* Make sure zero length keys are marked as bad */
732 set= 1;
733 rc= memcached_behavior_set(clone, MEMCACHED_BEHAVIOR_VERIFY_KEY, set);
734 assert(rc == MEMCACHED_SUCCESS);
735 string= memcached_get(clone, key, 0,
736 &string_length, &flags, &rc);
737 assert(rc == MEMCACHED_BAD_KEY_PROVIDED);
738 assert(string_length == 0);
739 assert(!string);
740
741 memcached_free(clone);
742
743 return 0;
744 }
745
746 #define READ_THROUGH_VALUE "set for me"
747 static memcached_return read_through_trigger(memcached_st *memc __attribute__((unused)),
748 char *key __attribute__((unused)),
749 size_t key_length __attribute__((unused)),
750 memcached_result_st *result)
751 {
752
753 return memcached_result_set_value(result, READ_THROUGH_VALUE, strlen(READ_THROUGH_VALUE));
754 }
755
756 static test_return read_through(memcached_st *memc)
757 {
758 memcached_return rc;
759 char *key= "foo";
760 char *string;
761 size_t string_length;
762 uint32_t flags;
763 memcached_trigger_key cb= (memcached_trigger_key)read_through_trigger;
764
765 string= memcached_get(memc, key, strlen(key),
766 &string_length, &flags, &rc);
767
768 assert(rc == MEMCACHED_NOTFOUND);
769 assert(string_length == 0);
770 assert(!string);
771
772 rc= memcached_callback_set(memc, MEMCACHED_CALLBACK_GET_FAILURE,
773 *(void **)&cb);
774 assert(rc == MEMCACHED_SUCCESS);
775
776 string= memcached_get(memc, key, strlen(key),
777 &string_length, &flags, &rc);
778
779 assert(rc == MEMCACHED_SUCCESS);
780 assert(string_length == strlen(READ_THROUGH_VALUE));
781 assert(!strcmp(READ_THROUGH_VALUE, string));
782 free(string);
783
784 string= memcached_get(memc, key, strlen(key),
785 &string_length, &flags, &rc);
786
787 assert(rc == MEMCACHED_SUCCESS);
788 assert(string_length == strlen(READ_THROUGH_VALUE));
789 assert(!strcmp(READ_THROUGH_VALUE, string));
790 free(string);
791
792 return 0;
793 }
794
795 static memcached_return delete_trigger(memcached_st *ptr __attribute__((unused)),
796 const char *key,
797 size_t key_length __attribute__((unused)))
798 {
799 assert(key);
800
801 return MEMCACHED_SUCCESS;
802 }
803
804 static test_return delete_through(memcached_st *memc)
805 {
806 memcached_trigger_delete_key callback;
807 memcached_return rc;
808
809 callback= (memcached_trigger_delete_key)delete_trigger;
810
811 rc= memcached_callback_set(memc, MEMCACHED_CALLBACK_DELETE_TRIGGER, *(void**)&callback);
812 assert(rc == MEMCACHED_SUCCESS);
813
814 return 0;
815 }
816
817 static test_return get_test(memcached_st *memc)
818 {
819 memcached_return rc;
820 char *key= "foo";
821 char *string;
822 size_t string_length;
823 uint32_t flags;
824
825 rc= memcached_delete(memc, key, strlen(key), (time_t)0);
826 assert(rc == MEMCACHED_BUFFERED || rc == MEMCACHED_NOTFOUND);
827
828 string= memcached_get(memc, key, strlen(key),
829 &string_length, &flags, &rc);
830
831 assert(rc == MEMCACHED_NOTFOUND);
832 assert(string_length == 0);
833 assert(!string);
834
835 return 0;
836 }
837
838 static test_return get_test2(memcached_st *memc)
839 {
840 memcached_return rc;
841 char *key= "foo";
842 char *value= "when we sanitize";
843 char *string;
844 size_t string_length;
845 uint32_t flags;
846
847 rc= memcached_set(memc, key, strlen(key),
848 value, strlen(value),
849 (time_t)0, (uint32_t)0);
850 assert(rc == MEMCACHED_SUCCESS || rc == MEMCACHED_BUFFERED);
851
852 string= memcached_get(memc, key, strlen(key),
853 &string_length, &flags, &rc);
854
855 assert(string);
856 assert(rc == MEMCACHED_SUCCESS);
857 assert(string_length == strlen(value));
858 assert(!memcmp(string, value, string_length));
859
860 free(string);
861
862 return 0;
863 }
864
865 static test_return set_test2(memcached_st *memc)
866 {
867 memcached_return rc;
868 char *key= "foo";
869 char *value= "train in the brain";
870 size_t value_length= strlen(value);
871 unsigned int x;
872
873 for (x= 0; x < 10; x++)
874 {
875 rc= memcached_set(memc, key, strlen(key),
876 value, value_length,
877 (time_t)0, (uint32_t)0);
878 assert(rc == MEMCACHED_SUCCESS || rc == MEMCACHED_BUFFERED);
879 }
880
881 return 0;
882 }
883
884 static test_return set_test3(memcached_st *memc)
885 {
886 memcached_return rc;
887 char *value;
888 size_t value_length= 8191;
889 unsigned int x;
890
891 value = (char*)malloc(value_length);
892 assert(value);
893
894 for (x= 0; x < value_length; x++)
895 value[x] = (char) (x % 127);
896
897 /* The dump test relies on there being at least 32 items in memcached */
898 for (x= 0; x < 32; x++)
899 {
900 char key[16];
901
902 sprintf(key, "foo%u", x);
903
904 rc= memcached_set(memc, key, strlen(key),
905 value, value_length,
906 (time_t)0, (uint32_t)0);
907 assert(rc == MEMCACHED_SUCCESS || rc == MEMCACHED_BUFFERED);
908 }
909
910 free(value);
911
912 return 0;
913 }
914
915 static test_return get_test3(memcached_st *memc)
916 {
917 memcached_return rc;
918 char *key= "foo";
919 char *value;
920 size_t value_length= 8191;
921 char *string;
922 size_t string_length;
923 uint32_t flags;
924 uint32_t x;
925
926 value = (char*)malloc(value_length);
927 assert(value);
928
929 for (x= 0; x < value_length; x++)
930 value[x] = (char) (x % 127);
931
932 rc= memcached_set(memc, key, strlen(key),
933 value, value_length,
934 (time_t)0, (uint32_t)0);
935 assert(rc == MEMCACHED_SUCCESS || rc == MEMCACHED_BUFFERED);
936
937 string= memcached_get(memc, key, strlen(key),
938 &string_length, &flags, &rc);
939
940 assert(rc == MEMCACHED_SUCCESS);
941 assert(string);
942 assert(string_length == value_length);
943 assert(!memcmp(string, value, string_length));
944
945 free(string);
946 free(value);
947
948 return 0;
949 }
950
951 static test_return get_test4(memcached_st *memc)
952 {
953 memcached_return rc;
954 char *key= "foo";
955 char *value;
956 size_t value_length= 8191;
957 char *string;
958 size_t string_length;
959 uint32_t flags;
960 uint32_t x;
961
962 value = (char*)malloc(value_length);
963 assert(value);
964
965 for (x= 0; x < value_length; x++)
966 value[x] = (char) (x % 127);
967
968 rc= memcached_set(memc, key, strlen(key),
969 value, value_length,
970 (time_t)0, (uint32_t)0);
971 assert(rc == MEMCACHED_SUCCESS || rc == MEMCACHED_BUFFERED);
972
973 for (x= 0; x < 10; x++)
974 {
975 string= memcached_get(memc, key, strlen(key),
976 &string_length, &flags, &rc);
977
978 assert(rc == MEMCACHED_SUCCESS);
979 assert(string);
980 assert(string_length == value_length);
981 assert(!memcmp(string, value, string_length));
982 free(string);
983 }
984
985 free(value);
986
987 return 0;
988 }
989
990 /*
991 * This test verifies that memcached_read_one_response doesn't try to
992 * dereference a NIL-pointer if you issue a multi-get and don't read out all
993 * responses before you execute a storage command.
994 */
995 static test_return get_test5(memcached_st *memc)
996 {
997 /*
998 ** Request the same key twice, to ensure that we hash to the same server
999 ** (so that we have multiple response values queued up) ;-)
1000 */
1001 char *keys[]= { "key", "key" };
1002 size_t lengths[]= { 3, 3 };
1003 uint32_t flags;
1004 size_t rlen;
1005
1006 memcached_return rc= memcached_set(memc, keys[0], lengths[0],
1007 keys[0], lengths[0], 0, 0);
1008 assert(rc == MEMCACHED_SUCCESS);
1009 rc= memcached_mget(memc, keys, lengths, 2);
1010
1011 memcached_result_st results_obj;
1012 memcached_result_st *results;
1013 results=memcached_result_create(memc, &results_obj);
1014 assert(results);
1015 results=memcached_fetch_result(memc, &results_obj, &rc);
1016 assert(results);
1017 memcached_result_free(&results_obj);
1018
1019 /* Don't read out the second result, but issue a set instead.. */
1020 rc= memcached_set(memc, keys[0], lengths[0], keys[0], lengths[0], 0, 0);
1021 assert(rc == MEMCACHED_SUCCESS);
1022
1023 char *val= memcached_get_by_key(memc, keys[0], lengths[0], "yek", 3,
1024 &rlen, &flags, &rc);
1025 assert(val == NULL);
1026 assert(rc == MEMCACHED_NOTFOUND);
1027 val= memcached_get(memc, keys[0], lengths[0], &rlen, &flags, &rc);
1028 assert(val != NULL);
1029 assert(rc == MEMCACHED_SUCCESS);
1030 free(val);
1031
1032 return TEST_SUCCESS;
1033 }
1034
1035 /* Do not copy the style of this code, I just access hosts to testthis function */
1036 static test_return stats_servername_test(memcached_st *memc)
1037 {
1038 memcached_return rc;
1039 memcached_stat_st stat;
1040 rc= memcached_stat_servername(&stat, NULL,
1041 memc->hosts[0].hostname,
1042 memc->hosts[0].port);
1043
1044 return 0;
1045 }
1046
1047 static test_return increment_test(memcached_st *memc)
1048 {
1049 uint64_t new_number;
1050 memcached_return rc;
1051 char *key= "number";
1052 char *value= "0";
1053
1054 rc= memcached_set(memc, key, strlen(key),
1055 value, strlen(value),
1056 (time_t)0, (uint32_t)0);
1057 assert(rc == MEMCACHED_SUCCESS || rc == MEMCACHED_BUFFERED);
1058
1059 rc= memcached_increment(memc, key, strlen(key),
1060 1, &new_number);
1061 assert(rc == MEMCACHED_SUCCESS);
1062 assert(new_number == 1);
1063
1064 rc= memcached_increment(memc, key, strlen(key),
1065 1, &new_number);
1066 assert(rc == MEMCACHED_SUCCESS);
1067 assert(new_number == 2);
1068
1069 return 0;
1070 }
1071
1072 static test_return increment_with_initial_test(memcached_st *memc)
1073 {
1074 if (memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_BINARY_PROTOCOL) != 0)
1075 {
1076 uint64_t new_number;
1077 memcached_return rc;
1078 char *key= "number";
1079 uint64_t initial= 0;
1080
1081 rc= memcached_increment_with_initial(memc, key, strlen(key),
1082 1, initial, 0, &new_number);
1083 assert(rc == MEMCACHED_SUCCESS);
1084 assert(new_number == initial);
1085
1086 rc= memcached_increment_with_initial(memc, key, strlen(key),
1087 1, initial, 0, &new_number);
1088 assert(rc == MEMCACHED_SUCCESS);
1089 assert(new_number == (initial + 1));
1090 }
1091 return 0;
1092 }
1093
1094 static test_return decrement_test(memcached_st *memc)
1095 {
1096 uint64_t new_number;
1097 memcached_return rc;
1098 char *key= "number";
1099 char *value= "3";
1100
1101 rc= memcached_set(memc, key, strlen(key),
1102 value, strlen(value),
1103 (time_t)0, (uint32_t)0);
1104 assert(rc == MEMCACHED_SUCCESS || rc == MEMCACHED_BUFFERED);
1105
1106 rc= memcached_decrement(memc, key, strlen(key),
1107 1, &new_number);
1108 assert(rc == MEMCACHED_SUCCESS);
1109 assert(new_number == 2);
1110
1111 rc= memcached_decrement(memc, key, strlen(key),
1112 1, &new_number);
1113 assert(rc == MEMCACHED_SUCCESS);
1114 assert(new_number == 1);
1115
1116 return 0;
1117 }
1118
1119 static test_return decrement_with_initial_test(memcached_st *memc)
1120 {
1121 if (memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_BINARY_PROTOCOL) != 0)
1122 {
1123 uint64_t new_number;
1124 memcached_return rc;
1125 char *key= "number";
1126 uint64_t initial= 3;
1127
1128 rc= memcached_decrement_with_initial(memc, key, strlen(key),
1129 1, initial, 0, &new_number);
1130 assert(rc == MEMCACHED_SUCCESS);
1131 assert(new_number == initial);
1132
1133 rc= memcached_decrement_with_initial(memc, key, strlen(key),
1134 1, initial, 0, &new_number);
1135 assert(rc == MEMCACHED_SUCCESS);
1136 assert(new_number == (initial - 1));
1137 }
1138 return 0;
1139 }
1140
1141 static test_return quit_test(memcached_st *memc)
1142 {
1143 memcached_return rc;
1144 char *key= "fudge";
1145 char *value= "sanford and sun";
1146
1147 rc= memcached_set(memc, key, strlen(key),
1148 value, strlen(value),
1149 (time_t)10, (uint32_t)3);
1150 assert(rc == MEMCACHED_SUCCESS || rc == MEMCACHED_BUFFERED);
1151 memcached_quit(memc);
1152
1153 rc= memcached_set(memc, key, strlen(key),
1154 value, strlen(value),
1155 (time_t)50, (uint32_t)9);
1156 assert(rc == MEMCACHED_SUCCESS || rc == MEMCACHED_BUFFERED);
1157
1158 return 0;
1159 }
1160
1161 static test_return mget_result_test(memcached_st *memc)
1162 {
1163 memcached_return rc;
1164 char *keys[]= {"fudge", "son", "food"};
1165 size_t key_length[]= {5, 3, 4};
1166 unsigned int x;
1167
1168 memcached_result_st results_obj;
1169 memcached_result_st *results;
1170
1171 results= memcached_result_create(memc, &results_obj);
1172 assert(results);
1173 assert(&results_obj == results);
1174
1175 /* We need to empty the server before continueing test */
1176 rc= memcached_flush(memc, 0);
1177 assert(rc == MEMCACHED_SUCCESS);
1178
1179 rc= memcached_mget(memc, keys, key_length, 3);
1180 assert(rc == MEMCACHED_SUCCESS);
1181
1182 while ((results= memcached_fetch_result(memc, &results_obj, &rc)) != NULL)
1183 {
1184 assert(results);
1185 }
1186
1187 while ((results= memcached_fetch_result(memc, &results_obj, &rc)) != NULL)
1188 assert(!results);
1189 assert(rc == MEMCACHED_END);
1190
1191 for (x= 0; x < 3; x++)
1192 {
1193 rc= memcached_set(memc, keys[x], key_length[x],
1194 keys[x], key_length[x],
1195 (time_t)50, (uint32_t)9);
1196 assert(rc == MEMCACHED_SUCCESS || rc == MEMCACHED_BUFFERED);
1197 }
1198
1199 rc= memcached_mget(memc, keys, key_length, 3);
1200 assert(rc == MEMCACHED_SUCCESS);
1201
1202 while ((results= memcached_fetch_result(memc, &results_obj, &rc)))
1203 {
1204 assert(results);
1205 assert(&results_obj == results);
1206 assert(rc == MEMCACHED_SUCCESS);
1207 assert(memcached_result_key_length(results) == memcached_result_length(results));
1208 assert(!memcmp(memcached_result_key_value(results),
1209 memcached_result_value(results),
1210 memcached_result_length(results)));
1211 }
1212
1213 memcached_result_free(&results_obj);
1214
1215 return 0;
1216 }
1217
1218 static test_return mget_result_alloc_test(memcached_st *memc)
1219 {
1220 memcached_return rc;
1221 char *keys[]= {"fudge", "son", "food"};
1222 size_t key_length[]= {5, 3, 4};
1223 unsigned int x;
1224
1225 memcached_result_st *results;
1226
1227 /* We need to empty the server before continueing test */
1228 rc= memcached_flush(memc, 0);
1229 assert(rc == MEMCACHED_SUCCESS);
1230
1231 rc= memcached_mget(memc, keys, key_length, 3);
1232 assert(rc == MEMCACHED_SUCCESS);
1233
1234 while ((results= memcached_fetch_result(memc, NULL, &rc)) != NULL)
1235 {
1236 assert(results);
1237 }
1238 assert(!results);
1239 assert(rc == MEMCACHED_END);
1240
1241 for (x= 0; x < 3; x++)
1242 {
1243 rc= memcached_set(memc, keys[x], key_length[x],
1244 keys[x], key_length[x],
1245 (time_t)50, (uint32_t)9);
1246 assert(rc == MEMCACHED_SUCCESS || rc == MEMCACHED_BUFFERED);
1247 }
1248
1249 rc= memcached_mget(memc, keys, key_length, 3);
1250 assert(rc == MEMCACHED_SUCCESS);
1251
1252 x= 0;
1253 while ((results= memcached_fetch_result(memc, NULL, &rc)))
1254 {
1255 assert(results);
1256 assert(rc == MEMCACHED_SUCCESS);
1257 assert(memcached_result_key_length(results) == memcached_result_length(results));
1258 assert(!memcmp(memcached_result_key_value(results),
1259 memcached_result_value(results),
1260 memcached_result_length(results)));
1261 memcached_result_free(results);
1262 x++;
1263 }
1264
1265 return 0;
1266 }
1267
1268 /* Count the results */
1269 static memcached_return callback_counter(memcached_st *ptr __attribute__((unused)),
1270 memcached_result_st *result __attribute__((unused)),
1271 void *context)
1272 {
1273 unsigned int *counter= (unsigned int *)context;
1274
1275 *counter= *counter + 1;
1276
1277 return MEMCACHED_SUCCESS;
1278 }
1279
1280 static test_return mget_result_function(memcached_st *memc)
1281 {
1282 memcached_return rc;
1283 char *keys[]= {"fudge", "son", "food"};
1284 size_t key_length[]= {5, 3, 4};
1285 unsigned int x;
1286 unsigned int counter;
1287 memcached_execute_function callbacks[1];
1288
1289 /* We need to empty the server before continueing test */
1290 rc= memcached_flush(memc, 0);
1291 for (x= 0; x < 3; x++)
1292 {
1293 rc= memcached_set(memc, keys[x], key_length[x],
1294 keys[x], key_length[x],
1295 (time_t)50, (uint32_t)9);
1296 assert(rc == MEMCACHED_SUCCESS || rc == MEMCACHED_BUFFERED);
1297 }
1298
1299 rc= memcached_mget(memc, keys, key_length, 3);
1300 assert(rc == MEMCACHED_SUCCESS);
1301
1302 callbacks[0]= &callback_counter;
1303 counter= 0;
1304 rc= memcached_fetch_execute(memc, callbacks, (void *)&counter, 1);
1305
1306 assert(counter == 3);
1307
1308 return 0;
1309 }
1310
1311 static test_return mget_test(memcached_st *memc)
1312 {
1313 memcached_return rc;
1314 char *keys[]= {"fudge", "son", "food"};
1315 size_t key_length[]= {5, 3, 4};
1316 unsigned int x;
1317 uint32_t flags;
1318
1319 char return_key[MEMCACHED_MAX_KEY];
1320 size_t return_key_length;
1321 char *return_value;
1322 size_t return_value_length;
1323
1324 /* We need to empty the server before continueing test */
1325 rc= memcached_flush(memc, 0);
1326 assert(rc == MEMCACHED_SUCCESS);
1327
1328 rc= memcached_mget(memc, keys, key_length, 3);
1329 assert(rc == MEMCACHED_SUCCESS);
1330
1331 while ((return_value= memcached_fetch(memc, return_key, &return_key_length,
1332 &return_value_length, &flags, &rc)) != NULL)
1333 {
1334 assert(return_value);
1335 }
1336 assert(!return_value);
1337 assert(return_value_length == 0);
1338 assert(rc == MEMCACHED_END);
1339
1340 for (x= 0; x < 3; x++)
1341 {
1342 rc= memcached_set(memc, keys[x], key_length[x],
1343 keys[x], key_length[x],
1344 (time_t)50, (uint32_t)9);
1345 assert(rc == MEMCACHED_SUCCESS || rc == MEMCACHED_BUFFERED);
1346 }
1347
1348 rc= memcached_mget(memc, keys, key_length, 3);
1349 assert(rc == MEMCACHED_SUCCESS);
1350
1351 x= 0;
1352 while ((return_value= memcached_fetch(memc, return_key, &return_key_length,
1353 &return_value_length, &flags, &rc)))
1354 {
1355 assert(return_value);
1356 assert(rc == MEMCACHED_SUCCESS);
1357 assert(return_key_length == return_value_length);
1358 assert(!memcmp(return_value, return_key, return_value_length));
1359 free(return_value);
1360 x++;
1361 }
1362
1363 return 0;
1364 }
1365
1366 static test_return get_stats_keys(memcached_st *memc)
1367 {
1368 char **list;
1369 char **ptr;
1370 memcached_stat_st stat;
1371 memcached_return rc;
1372
1373 list= memcached_stat_get_keys(memc, &stat, &rc);
1374 assert(rc == MEMCACHED_SUCCESS);
1375 for (ptr= list; *ptr; ptr++)
1376 assert(*ptr);
1377 fflush(stdout);
1378
1379 free(list);
1380
1381 return 0;
1382 }
1383
1384 static test_return version_string_test(memcached_st *memc __attribute__((unused)))
1385 {
1386 const char *version_string;
1387
1388 version_string= memcached_lib_version();
1389
1390 assert(!strcmp(version_string, LIBMEMCACHED_VERSION_STRING));
1391
1392 return 0;
1393 }
1394
1395 static test_return get_stats(memcached_st *memc)
1396 {
1397 unsigned int x;
1398 char **list;
1399 char **ptr;
1400 memcached_return rc;
1401 memcached_stat_st *stat;
1402
1403 stat= memcached_stat(memc, NULL, &rc);
1404 assert(rc == MEMCACHED_SUCCESS);
1405
1406 assert(rc == MEMCACHED_SUCCESS);
1407 assert(stat);
1408
1409 for (x= 0; x < memcached_server_count(memc); x++)
1410 {
1411 list= memcached_stat_get_keys(memc, stat+x, &rc);
1412 assert(rc == MEMCACHED_SUCCESS);
1413 for (ptr= list; *ptr; ptr++);
1414
1415 free(list);
1416 }
1417
1418 memcached_stat_free(NULL, stat);
1419
1420 return 0;
1421 }
1422
1423 static test_return add_host_test(memcached_st *memc)
1424 {
1425 unsigned int x;
1426 memcached_server_st *servers;
1427 memcached_return rc;
1428 char servername[]= "0.example.com";
1429
1430 servers= memcached_server_list_append_with_weight(NULL, servername, 400, 0, &rc);
1431 assert(servers);
1432 assert(1 == memcached_server_list_count(servers));
1433
1434 for (x= 2; x < 20; x++)
1435 {
1436 char buffer[SMALL_STRING_LEN];
1437
1438 snprintf(buffer, SMALL_STRING_LEN, "%u.example.com", 400+x);
1439 servers= memcached_server_list_append_with_weight(servers, buffer, 401, 0,
1440 &rc);
1441 assert(rc == MEMCACHED_SUCCESS);
1442 assert(x == memcached_server_list_count(servers));
1443 }
1444
1445 rc= memcached_server_push(memc, servers);
1446 assert(rc == MEMCACHED_SUCCESS);
1447 rc= memcached_server_push(memc, servers);
1448 assert(rc == MEMCACHED_SUCCESS);
1449
1450 memcached_server_list_free(servers);
1451
1452 return 0;
1453 }
1454
1455 static memcached_return clone_test_callback(memcached_st *parent __attribute__((unused)), memcached_st *clone __attribute__((unused)))
1456 {
1457 return MEMCACHED_SUCCESS;
1458 }
1459
1460 static memcached_return cleanup_test_callback(memcached_st *ptr __attribute__((unused)))
1461 {
1462 return MEMCACHED_SUCCESS;
1463 }
1464
1465 static test_return callback_test(memcached_st *memc)
1466 {
1467 /* Test User Data */
1468 {
1469 int x= 5;
1470 int *test_ptr;
1471 memcached_return rc;
1472
1473 rc= memcached_callback_set(memc, MEMCACHED_CALLBACK_USER_DATA, &x);
1474 assert(rc == MEMCACHED_SUCCESS);
1475 test_ptr= (int *)memcached_callback_get(memc, MEMCACHED_CALLBACK_USER_DATA, &rc);
1476 assert(*test_ptr == x);
1477 }
1478
1479 /* Test Clone Callback */
1480 {
1481 memcached_clone_func clone_cb= (memcached_clone_func)clone_test_callback;
1482 void *clone_cb_ptr= *(void **)&clone_cb;
1483 void *temp_function= NULL;
1484 memcached_return rc;
1485
1486 rc= memcached_callback_set(memc, MEMCACHED_CALLBACK_CLONE_FUNCTION,
1487 clone_cb_ptr);
1488 assert(rc == MEMCACHED_SUCCESS);
1489 temp_function= memcached_callback_get(memc, MEMCACHED_CALLBACK_CLONE_FUNCTION, &rc);
1490 assert(temp_function == clone_cb_ptr);
1491 }
1492
1493 /* Test Cleanup Callback */
1494 {
1495 memcached_cleanup_func cleanup_cb=
1496 (memcached_cleanup_func)cleanup_test_callback;
1497 void *cleanup_cb_ptr= *(void **)&cleanup_cb;
1498 void *temp_function= NULL;
1499 memcached_return rc;
1500
1501 rc= memcached_callback_set(memc, MEMCACHED_CALLBACK_CLONE_FUNCTION,
1502 cleanup_cb_ptr);
1503 assert(rc == MEMCACHED_SUCCESS);
1504 temp_function= memcached_callback_get(memc, MEMCACHED_CALLBACK_CLONE_FUNCTION, &rc);
1505 assert(temp_function == cleanup_cb_ptr);
1506 }
1507
1508 return 0;
1509 }
1510
1511 /* We don't test the behavior itself, we test the switches */
1512 static test_return behavior_test(memcached_st *memc)
1513 {
1514 uint64_t value;
1515 uint32_t set= 1;
1516
1517 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_NO_BLOCK, set);
1518 value= memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_NO_BLOCK);
1519 assert(value == 1);
1520
1521 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_TCP_NODELAY, set);
1522 value= memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_TCP_NODELAY);
1523 assert(value == 1);
1524
1525 set= MEMCACHED_HASH_MD5;
1526 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_HASH, set);
1527 value= memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_HASH);
1528 assert(value == MEMCACHED_HASH_MD5);
1529
1530 set= 0;
1531
1532 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_NO_BLOCK, set);
1533 value= memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_NO_BLOCK);
1534 assert(value == 0);
1535
1536 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_TCP_NODELAY, set);
1537 value= memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_TCP_NODELAY);
1538 assert(value == 0);
1539
1540 set= MEMCACHED_HASH_DEFAULT;
1541 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_HASH, set);
1542 value= memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_HASH);
1543 assert(value == MEMCACHED_HASH_DEFAULT);
1544
1545 set= MEMCACHED_HASH_CRC;
1546 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_HASH, set);
1547 value= memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_HASH);
1548 assert(value == MEMCACHED_HASH_CRC);
1549
1550 value= memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_SOCKET_SEND_SIZE);
1551 assert(value > 0);
1552
1553 value= memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_SOCKET_RECV_SIZE);
1554 assert(value > 0);
1555
1556 value= memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_NUMBER_OF_REPLICAS);
1557 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_NUMBER_OF_REPLICAS, value + 1);
1558 assert((value + 1) == memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_NUMBER_OF_REPLICAS));
1559 return 0;
1560 }
1561
1562 /* Test case provided by Cal Haldenbrand */
1563 static test_return user_supplied_bug1(memcached_st *memc)
1564 {
1565 unsigned int setter= 1;
1566 unsigned int x;
1567
1568 unsigned long long total= 0;
1569 uint32_t size= 0;
1570 char key[10];
1571 char randomstuff[6 * 1024];
1572 memcached_return rc;
1573
1574 memset(randomstuff, 0, 6 * 1024);
1575
1576 /* We just keep looking at the same values over and over */
1577 srandom(10);
1578
1579 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_NO_BLOCK, setter);
1580 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_TCP_NODELAY, setter);
1581
1582
1583 /* add key */
1584 for (x= 0 ; total < 20 * 1024576 ; x++ )
1585 {
1586 unsigned int j= 0;
1587
1588 size= (rand() % ( 5 * 1024 ) ) + 400;
1589 memset(randomstuff, 0, 6 * 1024);
1590 assert(size < 6 * 1024); /* Being safe here */
1591
1592 for (j= 0 ; j < size ;j++)
1593 randomstuff[j] = (char) (rand() % 26) + 97;
1594
1595 total += size;
1596 sprintf(key, "%d", x);
1597 rc = memcached_set(memc, key, strlen(key),
1598 randomstuff, strlen(randomstuff), 10, 0);
1599 assert(rc == MEMCACHED_SUCCESS || rc == MEMCACHED_BUFFERED);
1600 /* If we fail, lets try again */
1601 if (rc != MEMCACHED_SUCCESS && rc != MEMCACHED_BUFFERED)
1602 rc = memcached_set(memc, key, strlen(key),
1603 randomstuff, strlen(randomstuff), 10, 0);
1604 assert(rc == MEMCACHED_SUCCESS || rc == MEMCACHED_BUFFERED);
1605 }
1606
1607 return 0;
1608 }
1609
1610 /* Test case provided by Cal Haldenbrand */
1611 static test_return user_supplied_bug2(memcached_st *memc)
1612 {
1613 int errors;
1614 unsigned int setter;
1615 unsigned int x;
1616 unsigned long long total;
1617
1618 setter= 1;
1619 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_NO_BLOCK, setter);
1620 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_TCP_NODELAY, setter);
1621 #ifdef NOT_YET
1622 setter = 20 * 1024576;
1623 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_SOCKET_SEND_SIZE, setter);
1624 setter = 20 * 1024576;
1625 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_SOCKET_RECV_SIZE, setter);
1626 getter = memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_SOCKET_SEND_SIZE);
1627 getter = memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_SOCKET_RECV_SIZE);
1628
1629 for (x= 0, errors= 0, total= 0 ; total < 20 * 1024576 ; x++)
1630 #endif
1631
1632 for (x= 0, errors= 0, total= 0 ; total < 24576 ; x++)
1633 {
1634 memcached_return rc= MEMCACHED_SUCCESS;
1635 char buffer[SMALL_STRING_LEN];
1636 uint32_t flags= 0;
1637 size_t val_len= 0;
1638 char *getval;
1639
1640 memset(buffer, 0, SMALL_STRING_LEN);
1641
1642 snprintf(buffer, SMALL_STRING_LEN, "%u", x);
1643 getval= memcached_get(memc, buffer, strlen(buffer),
1644 &val_len, &flags, &rc);
1645 if (rc != MEMCACHED_SUCCESS)
1646 {
1647 if (rc == MEMCACHED_NOTFOUND)
1648 errors++;
1649 else
1650 {
1651 WATCHPOINT_ERROR(rc);
1652 assert(0);
1653 }
1654
1655 continue;
1656 }
1657 total+= val_len;
1658 errors= 0;
1659 free(getval);
1660 }
1661
1662 return 0;
1663 }
1664
1665 /* Do a large mget() over all the keys we think exist */
1666 #define KEY_COUNT 3000 // * 1024576
1667 static test_return user_supplied_bug3(memcached_st *memc)
1668 {
1669 memcached_return rc;
1670 unsigned int setter;
1671 unsigned int x;
1672 char **keys;
1673 size_t key_lengths[KEY_COUNT];
1674
1675 setter= 1;
1676 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_NO_BLOCK, setter);
1677 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_TCP_NODELAY, setter);
1678 #ifdef NOT_YET
1679 setter = 20 * 1024576;
1680 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_SOCKET_SEND_SIZE, setter);
1681 setter = 20 * 1024576;
1682 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_SOCKET_RECV_SIZE, setter);
1683 getter = memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_SOCKET_SEND_SIZE);
1684 getter = memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_SOCKET_RECV_SIZE);
1685 #endif
1686
1687 keys= (char **)malloc(sizeof(char *) * KEY_COUNT);
1688 assert(keys);
1689 memset(keys, 0, (sizeof(char *) * KEY_COUNT));
1690 for (x= 0; x < KEY_COUNT; x++)
1691 {
1692 char buffer[30];
1693
1694 snprintf(buffer, 30, "%u", x);
1695 keys[x]= strdup(buffer);
1696 key_lengths[x]= strlen(keys[x]);
1697 }
1698
1699 rc= memcached_mget(memc, keys, key_lengths, KEY_COUNT);
1700 assert(rc == MEMCACHED_SUCCESS);
1701
1702 /* Turn this into a help function */
1703 {
1704 char return_key[MEMCACHED_MAX_KEY];
1705 size_t return_key_length;
1706 char *return_value;
1707 size_t return_value_length;
1708 uint32_t flags;
1709
1710 while ((return_value= memcached_fetch(memc, return_key, &return_key_length,
1711 &return_value_length, &flags, &rc)))
1712 {
1713 assert(return_value);
1714 assert(rc == MEMCACHED_SUCCESS);
1715 free(return_value);
1716 }
1717 }
1718
1719 for (x= 0; x < KEY_COUNT; x++)
1720 free(keys[x]);
1721 free(keys);
1722
1723 return 0;
1724 }
1725
1726 /* Make sure we behave properly if server list has no values */
1727 static test_return user_supplied_bug4(memcached_st *memc)
1728 {
1729 memcached_return rc;
1730 char *keys[]= {"fudge", "son", "food"};
1731 size_t key_length[]= {5, 3, 4};
1732 unsigned int x;
1733 uint32_t flags;
1734 char return_key[MEMCACHED_MAX_KEY];
1735 size_t return_key_length;
1736 char *return_value;
1737 size_t return_value_length;
1738
1739 /* Here we free everything before running a bunch of mget tests */
1740 {
1741 memcached_server_list_free(memc->hosts);
1742 memc->hosts= NULL;
1743 memc->number_of_hosts= 0;
1744 }
1745
1746
1747 /* We need to empty the server before continueing test */
1748 rc= memcached_flush(memc, 0);
1749 assert(rc == MEMCACHED_NO_SERVERS);
1750
1751 rc= memcached_mget(memc, keys, key_length, 3);
1752 assert(rc == MEMCACHED_NO_SERVERS);
1753
1754 while ((return_value= memcached_fetch(memc, return_key, &return_key_length,
1755 &return_value_length, &flags, &rc)) != NULL)
1756 {
1757 assert(return_value);
1758 }
1759 assert(!return_value);
1760 assert(return_value_length == 0);
1761 assert(rc == MEMCACHED_NO_SERVERS);
1762
1763 for (x= 0; x < 3; x++)
1764 {
1765 rc= memcached_set(memc, keys[x], key_length[x],
1766 keys[x], key_length[x],
1767 (time_t)50, (uint32_t)9);
1768 assert(rc == MEMCACHED_NO_SERVERS);
1769 }
1770
1771 rc= memcached_mget(memc, keys, key_length, 3);
1772 assert(rc == MEMCACHED_NO_SERVERS);
1773
1774 x= 0;
1775 while ((return_value= memcached_fetch(memc, return_key, &return_key_length,
1776 &return_value_length, &flags, &rc)))
1777 {
1778 assert(return_value);
1779 assert(rc == MEMCACHED_SUCCESS);
1780 assert(return_key_length == return_value_length);
1781 assert(!memcmp(return_value, return_key, return_value_length));
1782 free(return_value);
1783 x++;
1784 }
1785
1786 return 0;
1787 }
1788
1789 #define VALUE_SIZE_BUG5 1048064
1790 static test_return user_supplied_bug5(memcached_st *memc)
1791 {
1792 memcached_return rc;
1793 char *keys[]= {"036790384900", "036790384902", "036790384904", "036790384906"};
1794 size_t key_length[]= {strlen("036790384900"), strlen("036790384902"), strlen("036790384904"), strlen("036790384906")};
1795 char return_key[MEMCACHED_MAX_KEY];
1796 size_t return_key_length;
1797 char *value;
1798 size_t value_length;
1799 uint32_t flags;
1800 unsigned int count;
1801 unsigned int x;
1802 char insert_data[VALUE_SIZE_BUG5];
1803
1804 for (x= 0; x < VALUE_SIZE_BUG5; x++)
1805 insert_data[x]= rand();
1806
1807 memcached_flush(memc, 0);
1808 value= memcached_get(memc, keys[0], key_length[0],
1809 &value_length, &flags, &rc);
1810 assert(value == NULL);
1811 rc= memcached_mget(memc, keys, key_length, 4);
1812
1813 count= 0;
1814 while ((value= memcached_fetch(memc, return_key, &return_key_length,
1815 &value_length, &flags, &rc)))
1816 count++;
1817 assert(count == 0);
1818
1819 for (x= 0; x < 4; x++)
1820 {
1821 rc= memcached_set(memc, keys[x], key_length[x],
1822 insert_data, VALUE_SIZE_BUG5,
1823 (time_t)0, (uint32_t)0);
1824 assert(rc == MEMCACHED_SUCCESS);
1825 }
1826
1827 for (x= 0; x < 10; x++)
1828 {
1829 value= memcached_get(memc, keys[0], key_length[0],
1830 &value_length, &flags, &rc);
1831 assert(value);
1832 free(value);
1833
1834 rc= memcached_mget(memc, keys, key_length, 4);
1835 count= 0;
1836 while ((value= memcached_fetch(memc, return_key, &return_key_length,
1837 &value_length, &flags, &rc)))
1838 {
1839 count++;
1840 free(value);
1841 }
1842 assert(count == 4);
1843 }
1844
1845 return 0;
1846 }
1847
1848 static test_return user_supplied_bug6(memcached_st *memc)
1849 {
1850 memcached_return rc;
1851 char *keys[]= {"036790384900", "036790384902", "036790384904", "036790384906"};
1852 size_t key_length[]= {strlen("036790384900"), strlen("036790384902"), strlen("036790384904"), strlen("036790384906")};
1853 char return_key[MEMCACHED_MAX_KEY];
1854 size_t return_key_length;
1855 char *value;
1856 size_t value_length;
1857 uint32_t flags;
1858 unsigned int count;
1859 unsigned int x;
1860 char insert_data[VALUE_SIZE_BUG5];
1861
1862 for (x= 0; x < VALUE_SIZE_BUG5; x++)
1863 insert_data[x]= rand();
1864
1865 memcached_flush(memc, 0);
1866 value= memcached_get(memc, keys[0], key_length[0],
1867 &value_length, &flags, &rc);
1868 assert(value == NULL);
1869 assert(rc == MEMCACHED_NOTFOUND);
1870 rc= memcached_mget(memc, keys, key_length, 4);
1871 assert(rc == MEMCACHED_SUCCESS);
1872
1873 count= 0;
1874 while ((value= memcached_fetch(memc, return_key, &return_key_length,
1875 &value_length, &flags, &rc)))
1876 count++;
1877 assert(count == 0);
1878 assert(rc == MEMCACHED_END);
1879
1880 for (x= 0; x < 4; x++)
1881 {
1882 rc= memcached_set(memc, keys[x], key_length[x],
1883 insert_data, VALUE_SIZE_BUG5,
1884 (time_t)0, (uint32_t)0);
1885 assert(rc == MEMCACHED_SUCCESS);
1886 }
1887
1888 for (x= 0; x < 2; x++)
1889 {
1890 value= memcached_get(memc, keys[0], key_length[0],
1891 &value_length, &flags, &rc);
1892 assert(value);
1893 free(value);
1894
1895 rc= memcached_mget(memc, keys, key_length, 4);
1896 assert(rc == MEMCACHED_SUCCESS);
1897 count= 3;
1898 /* We test for purge of partial complete fetches */
1899 for (count= 3; count; count--)
1900 {
1901 value= memcached_fetch(memc, return_key, &return_key_length,
1902 &value_length, &flags, &rc);
1903 assert(rc == MEMCACHED_SUCCESS);
1904 assert(!(memcmp(value, insert_data, value_length)));
1905 assert(value_length);
1906 free(value);
1907 }
1908 }
1909
1910 return 0;
1911 }
1912
1913 static test_return user_supplied_bug8(memcached_st *memc __attribute__((unused)))
1914 {
1915 memcached_return rc;
1916 memcached_st *mine;
1917 memcached_st *clone;
1918
1919 memcached_server_st *servers;
1920 char *server_list= "memcache1.memcache.bk.sapo.pt:11211, memcache1.memcache.bk.sapo.pt:11212, memcache1.memcache.bk.sapo.pt:11213, memcache1.memcache.bk.sapo.pt:11214, memcache2.memcache.bk.sapo.pt:11211, memcache2.memcache.bk.sapo.pt:11212, memcache2.memcache.bk.sapo.pt:11213, memcache2.memcache.bk.sapo.pt:11214";
1921
1922 servers= memcached_servers_parse(server_list);
1923 assert(servers);
1924
1925 mine= memcached_create(NULL);
1926 rc= memcached_server_push(mine, servers);
1927 assert(rc == MEMCACHED_SUCCESS);
1928 memcached_server_list_free(servers);
1929
1930 assert(mine);
1931 clone= memcached_clone(NULL, mine);
1932
1933 memcached_quit(mine);
1934 memcached_quit(clone);
1935
1936
1937 memcached_free(mine);
1938 memcached_free(clone);
1939
1940 return 0;
1941 }
1942
1943 /* Test flag store/retrieve */
1944 static test_return user_supplied_bug7(memcached_st *memc)
1945 {
1946 memcached_return rc;
1947 char *keys= "036790384900";
1948 size_t key_length= strlen("036790384900");
1949 char return_key[MEMCACHED_MAX_KEY];
1950 size_t return_key_length;
1951 char *value;
1952 size_t value_length;
1953 uint32_t flags;
1954 unsigned int x;
1955 char insert_data[VALUE_SIZE_BUG5];
1956
1957 for (x= 0; x < VALUE_SIZE_BUG5; x++)
1958 insert_data[x]= rand();
1959
1960 memcached_flush(memc, 0);
1961
1962 flags= 245;
1963 rc= memcached_set(memc, keys, key_length,
1964 insert_data, VALUE_SIZE_BUG5,
1965 (time_t)0, flags);
1966 assert(rc == MEMCACHED_SUCCESS);
1967
1968 flags= 0;
1969 value= memcached_get(memc, keys, key_length,
1970 &value_length, &flags, &rc);
1971 assert(flags == 245);
1972 assert(value);
1973 free(value);
1974
1975 rc= memcached_mget(memc, &keys, &key_length, 1);
1976
1977 flags= 0;
1978 value= memcached_fetch(memc, return_key, &return_key_length,
1979 &value_length, &flags, &rc);
1980 assert(flags == 245);
1981 assert(value);
1982 free(value);
1983
1984
1985 return 0;
1986 }
1987
1988 static test_return user_supplied_bug9(memcached_st *memc)
1989 {
1990 memcached_return rc;
1991 char *keys[]= {"UDATA:edevil@sapo.pt", "fudge&*@#", "for^#@&$not"};
1992 size_t key_length[3];
1993 unsigned int x;
1994 uint32_t flags;
1995 unsigned count= 0;
1996
1997 char return_key[MEMCACHED_MAX_KEY];
1998 size_t return_key_length;
1999 char *return_value;
2000 size_t return_value_length;
2001
2002
2003 key_length[0]= strlen("UDATA:edevil@sapo.pt");
2004 key_length[1]= strlen("fudge&*@#");
2005 key_length[2]= strlen("for^#@&$not");
2006
2007
2008 for (x= 0; x < 3; x++)
2009 {
2010 rc= memcached_set(memc, keys[x], key_length[x],
2011 keys[x], key_length[x],
2012 (time_t)50, (uint32_t)9);
2013 assert(rc == MEMCACHED_SUCCESS);
2014 }
2015
2016 rc= memcached_mget(memc, keys, key_length, 3);
2017 assert(rc == MEMCACHED_SUCCESS);
2018
2019 /* We need to empty the server before continueing test */
2020 while ((return_value= memcached_fetch(memc, return_key, &return_key_length,
2021 &return_value_length, &flags, &rc)) != NULL)
2022 {
2023 assert(return_value);
2024 free(return_value);
2025 count++;
2026 }
2027 assert(count == 3);
2028
2029 return 0;
2030 }
2031
2032 /* We are testing with aggressive timeout to get failures */
2033 static test_return user_supplied_bug10(memcached_st *memc)
2034 {
2035 char *key= "foo";
2036 char *value;
2037 size_t value_length= 512;
2038 unsigned int x;
2039 int key_len= 3;
2040 memcached_return rc;
2041 unsigned int set= 1;
2042 memcached_st *mclone= memcached_clone(NULL, memc);
2043 int32_t timeout;
2044
2045 memcached_behavior_set(mclone, MEMCACHED_BEHAVIOR_NO_BLOCK, set);
2046 memcached_behavior_set(mclone, MEMCACHED_BEHAVIOR_TCP_NODELAY, set);
2047 timeout= 2;
2048 memcached_behavior_set(mclone, MEMCACHED_BEHAVIOR_POLL_TIMEOUT, timeout);
2049
2050 value = (char*)malloc(value_length * sizeof(char));
2051
2052 for (x= 0; x < value_length; x++)
2053 value[x]= (char) (x % 127);
2054
2055 for (x= 1; x <= 100000; ++x)
2056 {
2057 rc= memcached_set(mclone, key, key_len,value, value_length, 0, 0);
2058
2059 assert(rc == MEMCACHED_SUCCESS || rc == MEMCACHED_WRITE_FAILURE ||
2060 rc == MEMCACHED_BUFFERED || rc == MEMCACHED_TIMEOUT);
2061
2062 if (rc == MEMCACHED_WRITE_FAILURE || rc == MEMCACHED_TIMEOUT)
2063 x--;
2064 }
2065
2066 free(value);
2067 memcached_free(mclone);
2068
2069 return 0;
2070 }
2071
2072 /*
2073 We are looking failures in the async protocol
2074 */
2075 static test_return user_supplied_bug11(memcached_st *memc)
2076 {
2077 char *key= "foo";
2078 char *value;
2079 size_t value_length= 512;
2080 unsigned int x;
2081 int key_len= 3;
2082 memcached_return rc;
2083 unsigned int set= 1;
2084 int32_t timeout;
2085 memcached_st *mclone= memcached_clone(NULL, memc);
2086
2087 memcached_behavior_set(mclone, MEMCACHED_BEHAVIOR_NO_BLOCK, set);
2088 memcached_behavior_set(mclone, MEMCACHED_BEHAVIOR_TCP_NODELAY, set);
2089 timeout= -1;
2090 memcached_behavior_set(mclone, MEMCACHED_BEHAVIOR_POLL_TIMEOUT, timeout);
2091
2092 timeout= (int32_t)memcached_behavior_get(mclone, MEMCACHED_BEHAVIOR_POLL_TIMEOUT);
2093
2094 assert(timeout == -1);
2095
2096 value = (char*)malloc(value_length * sizeof(char));
2097
2098 for (x= 0; x < value_length; x++)
2099 value[x]= (char) (x % 127);
2100
2101 for (x= 1; x <= 100000; ++x)
2102 {
2103 rc= memcached_set(mclone, key, key_len,value, value_length, 0, 0);
2104 }
2105
2106 free(value);
2107 memcached_free(mclone);
2108
2109 return 0;
2110 }
2111
2112 /*
2113 Bug found where incr was not returning MEMCACHED_NOTFOUND when object did not exist.
2114 */
2115 static test_return user_supplied_bug12(memcached_st *memc)
2116 {
2117 memcached_return rc;
2118 uint32_t flags;
2119 size_t value_length;
2120 char *value;
2121 uint64_t number_value;
2122
2123 value= memcached_get(memc, "autoincrement", strlen("autoincrement"),
2124 &value_length, &flags, &rc);
2125 assert(value == NULL);
2126 assert(rc == MEMCACHED_NOTFOUND);
2127
2128 rc= memcached_increment(memc, "autoincrement", strlen("autoincrement"),
2129 1, &number_value);
2130
2131 assert(value == NULL);
2132 /* The binary protocol will set the key if it doesn't exist */
2133 if (memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_BINARY_PROTOCOL) == 1)
2134 assert(rc == MEMCACHED_SUCCESS);
2135 else
2136 assert(rc == MEMCACHED_NOTFOUND);
2137
2138 rc= memcached_set(memc, "autoincrement", strlen("autoincrement"), "1", 1, 0, 0);
2139
2140 value= memcached_get(memc, "autoincrement", strlen("autoincrement"),
2141 &value_length, &flags, &rc);
2142 assert(value);
2143 assert(rc == MEMCACHED_SUCCESS);
2144 free(value);
2145
2146 rc= memcached_increment(memc, "autoincrement", strlen("autoincrement"),
2147 1, &number_value);
2148 assert(number_value == 2);
2149 assert(rc == MEMCACHED_SUCCESS);
2150
2151 return 0;
2152 }
2153
2154 /*
2155 Bug found where command total one more than MEMCACHED_MAX_BUFFER
2156 set key34567890 0 0 8169 \r\n is sent followed by buffer of size 8169, followed by 8169
2157 */
2158 static test_return user_supplied_bug13(memcached_st *memc)
2159 {
2160 char key[] = "key34567890";
2161 char *overflow;
2162 memcached_return rc;
2163 size_t overflowSize;
2164
2165 char commandFirst[]= "set key34567890 0 0 ";
2166 char commandLast[] = " \r\n"; /* first line of command sent to server */
2167 size_t commandLength;
2168 size_t testSize;
2169
2170 commandLength = strlen(commandFirst) + strlen(commandLast) + 4; /* 4 is number of characters in size, probably 8196 */
2171
2172 overflowSize = MEMCACHED_MAX_BUFFER - commandLength;
2173
2174 for (testSize= overflowSize - 1; testSize < overflowSize + 1; testSize++)
2175 {
2176 overflow= malloc(testSize);
2177 assert(overflow != NULL);
2178
2179 memset(overflow, 'x', testSize);
2180 rc= memcached_set(memc, key, strlen(key),
2181 overflow, testSize, 0, 0);
2182 assert(rc == MEMCACHED_SUCCESS);
2183 free(overflow);
2184 }
2185
2186 return 0;
2187 }
2188
2189
2190 /*
2191 Test values of many different sizes
2192 Bug found where command total one more than MEMCACHED_MAX_BUFFER
2193 set key34567890 0 0 8169 \r\n
2194 is sent followed by buffer of size 8169, followed by 8169
2195 */
2196 static test_return user_supplied_bug14(memcached_st *memc)
2197 {
2198 int setter= 1;
2199 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_TCP_NODELAY, setter);
2200 memcached_return rc;
2201 char *key= "foo";
2202 char *value;
2203 size_t value_length= 18000;
2204 char *string;
2205 size_t string_length;
2206 uint32_t flags;
2207 unsigned int x;
2208 size_t current_length;
2209
2210 value = (char*)malloc(value_length);
2211 assert(value);
2212
2213 for (x= 0; x < value_length; x++)
2214 value[x] = (char) (x % 127);
2215
2216 for (current_length= 0; current_length < value_length; current_length++)
2217 {
2218 rc= memcached_set(memc, key, strlen(key),
2219 value, current_length,
2220 (time_t)0, (uint32_t)0);
2221 assert(rc == MEMCACHED_SUCCESS || rc == MEMCACHED_BUFFERED);
2222
2223 string= memcached_get(memc, key, strlen(key),
2224 &string_length, &flags, &rc);
2225
2226 assert(rc == MEMCACHED_SUCCESS);
2227 assert(string_length == current_length);
2228 assert(!memcmp(string, value, string_length));
2229
2230 free(string);
2231 }
2232
2233 free(value);
2234
2235 return 0;
2236 }
2237
2238 /*
2239 Look for zero length value problems
2240 */
2241 static test_return user_supplied_bug15(memcached_st *memc)
2242 {
2243 uint32_t x;
2244 memcached_return rc;
2245 char *key= "mykey";
2246 char *value;
2247 size_t length;
2248 uint32_t flags;
2249
2250 for (x= 0; x < 2; x++)
2251 {
2252 rc= memcached_set(memc, key, strlen(key),
2253 NULL, 0,
2254 (time_t)0, (uint32_t)0);
2255
2256 assert(rc == MEMCACHED_SUCCESS);
2257
2258 value= memcached_get(memc, key, strlen(key),
2259 &length, &flags, &rc);
2260
2261 assert(rc == MEMCACHED_SUCCESS);
2262 assert(value == NULL);
2263 assert(length == 0);
2264 assert(flags == 0);
2265
2266 value= memcached_get(memc, key, strlen(key),
2267 &length, &flags, &rc);
2268
2269 assert(rc == MEMCACHED_SUCCESS);
2270 assert(value == NULL);
2271 assert(length == 0);
2272 assert(flags == 0);
2273 }
2274
2275 return 0;
2276 }
2277
2278 /* Check the return sizes on FLAGS to make sure it stores 32bit unsigned values correctly */
2279 static test_return user_supplied_bug16(memcached_st *memc)
2280 {
2281 memcached_return rc;
2282 char *key= "mykey";
2283 char *value;
2284 size_t length;
2285 uint32_t flags;
2286
2287 rc= memcached_set(memc, key, strlen(key),
2288 NULL, 0,
2289 (time_t)0, UINT32_MAX);
2290
2291 assert(rc == MEMCACHED_SUCCESS);
2292
2293 value= memcached_get(memc, key, strlen(key),
2294 &length, &flags, &rc);
2295
2296 assert(rc == MEMCACHED_SUCCESS);
2297 assert(value == NULL);
2298 assert(length == 0);
2299 assert(flags == UINT32_MAX);
2300
2301 return 0;
2302 }
2303
2304 /* Check the validity of chinese key*/
2305 static test_return user_supplied_bug17(memcached_st *memc)
2306 {
2307 memcached_return rc;
2308 char *key= "豆瓣";
2309 char *value="我们在炎热抑郁的夏天无法停止豆瓣";
2310 char *value2;
2311 size_t length;
2312 uint32_t flags;
2313
2314 rc= memcached_set(memc, key, strlen(key),
2315 value, strlen(value),
2316 (time_t)0, 0);
2317
2318 assert(rc == MEMCACHED_SUCCESS);
2319
2320 value2= memcached_get(memc, key, strlen(key),
2321 &length, &flags, &rc);
2322
2323 assert(length==strlen(value));
2324 assert(rc == MEMCACHED_SUCCESS);
2325 assert(memcmp(value, value2, length)==0);
2326 free(value2);
2327
2328 return 0;
2329 }
2330
2331 /*
2332 From Andrei on IRC
2333 */
2334
2335 static test_return user_supplied_bug19(memcached_st *memc)
2336 {
2337 memcached_st *m;
2338 memcached_server_st *s;
2339 memcached_return res;
2340
2341 (void)memc;
2342
2343 m= memcached_create(NULL);
2344 memcached_server_add_with_weight(m, "localhost", 11311, 100);
2345 memcached_server_add_with_weight(m, "localhost", 11312, 100);
2346
2347 s= memcached_server_by_key(m, "a", 1, &res);
2348 memcached_server_free(s);
2349
2350 memcached_free(m);
2351
2352 return 0;
2353 }
2354
2355 /* CAS test from Andei */
2356 static test_return user_supplied_bug20(memcached_st *memc)
2357 {
2358 memcached_return status;
2359 memcached_result_st *result, result_obj;
2360 char *key = "abc";
2361 size_t key_len = strlen("abc");
2362 char *value = "foobar";
2363 size_t value_len = strlen(value);
2364
2365 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_SUPPORT_CAS, 1);
2366
2367 status = memcached_set(memc, key, key_len, value, value_len, (time_t)0, (uint32_t)0);
2368 assert(status == MEMCACHED_SUCCESS);
2369
2370 status = memcached_mget(memc, &key, &key_len, 1);
2371 assert(status == MEMCACHED_SUCCESS);
2372
2373 result= memcached_result_create(memc, &result_obj);
2374 assert(result);
2375
2376 memcached_result_create(memc, &result_obj);
2377 result= memcached_fetch_result(memc, &result_obj, &status);
2378
2379 assert(result);
2380 assert(status == MEMCACHED_SUCCESS);
2381
2382 memcached_result_free(result);
2383
2384 return 0;
2385 }
2386
2387 #include "ketama_test_cases.h"
2388 static test_return user_supplied_bug18(memcached_st *trash)
2389 {
2390 memcached_return rc;
2391 int value;
2392 int x;
2393 memcached_server_st *server_pool;
2394 memcached_st *memc;
2395
2396 (void)trash;
2397
2398 memc= memcached_create(NULL);
2399 assert(memc);
2400
2401 rc= memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_KETAMA_WEIGHTED, 1);
2402 assert(rc == MEMCACHED_SUCCESS);
2403
2404 value= memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_KETAMA_WEIGHTED);
2405 assert(value == 1);
2406
2407 rc= memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_KETAMA_HASH, MEMCACHED_HASH_MD5);
2408 assert(rc == MEMCACHED_SUCCESS);
2409
2410 value= memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_KETAMA_HASH);
2411 assert(value == MEMCACHED_HASH_MD5);
2412
2413 server_pool = memcached_servers_parse("10.0.1.1:11211 600,10.0.1.2:11211 300,10.0.1.3:11211 200,10.0.1.4:11211 350,10.0.1.5:11211 1000,10.0.1.6:11211 800,10.0.1.7:11211 950,10.0.1.8:11211 100");
2414 memcached_server_push(memc, server_pool);
2415
2416 /* verify that the server list was parsed okay. */
2417 assert(memc->number_of_hosts == 8);
2418 assert(strcmp(server_pool[0].hostname, "10.0.1.1") == 0);
2419 assert(server_pool[0].port == 11211);
2420 assert(server_pool[0].weight == 600);
2421 assert(strcmp(server_pool[2].hostname, "10.0.1.3") == 0);
2422 assert(server_pool[2].port == 11211);
2423 assert(server_pool[2].weight == 200);
2424 assert(strcmp(server_pool[7].hostname, "10.0.1.8") == 0);
2425 assert(server_pool[7].port == 11211);
2426 assert(server_pool[7].weight == 100);
2427
2428 /* VDEAAAAA hashes to fffcd1b5, after the last continuum point, and lets
2429 * us test the boundary wraparound.
2430 */
2431 assert(memcached_generate_hash(memc, (char *)"VDEAAAAA", 8) == memc->continuum[0].index);
2432
2433 /* verify the standard ketama set. */
2434 for (x= 0; x < 99; x++)
2435 {
2436 uint32_t server_idx = memcached_generate_hash(memc, test_cases[x].key, strlen(test_cases[x].key));
2437 char *hostname = memc->hosts[server_idx].hostname;
2438 assert(strcmp(hostname, test_cases[x].server) == 0);
2439 }
2440
2441 memcached_server_list_free(server_pool);
2442 memcached_free(memc);
2443
2444 return 0;
2445 }
2446
2447 static test_return auto_eject_hosts(memcached_st *trash)
2448 {
2449 (void) trash;
2450
2451 memcached_return rc;
2452 memcached_st *memc= memcached_create(NULL);
2453 assert(memc);
2454
2455 rc= memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_KETAMA_WEIGHTED, 1);
2456 assert(rc == MEMCACHED_SUCCESS);
2457
2458 uint64_t value= memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_KETAMA_WEIGHTED);
2459 assert(value == 1);
2460
2461 rc= memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_KETAMA_HASH, MEMCACHED_HASH_MD5);
2462 assert(rc == MEMCACHED_SUCCESS);
2463
2464 value= memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_KETAMA_HASH);
2465 assert(value == MEMCACHED_HASH_MD5);
2466
2467 /* server should be removed when in delay */
2468 rc= memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_AUTO_EJECT_HOSTS, 1);
2469 assert(rc == MEMCACHED_SUCCESS);
2470
2471 value= memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_AUTO_EJECT_HOSTS);
2472 assert(value == 1);
2473
2474 memcached_server_st *server_pool;
2475 server_pool = memcached_servers_parse("10.0.1.1:11211 600,10.0.1.2:11211 300,10.0.1.3:11211 200,10.0.1.4:11211 350,10.0.1.5:11211 1000,10.0.1.6:11211 800,10.0.1.7:11211 950,10.0.1.8:11211 100");
2476 memcached_server_push(memc, server_pool);
2477
2478 /* verify that the server list was parsed okay. */
2479 assert(memc->number_of_hosts == 8);
2480 assert(strcmp(server_pool[0].hostname, "10.0.1.1") == 0);
2481 assert(server_pool[0].port == 11211);
2482 assert(server_pool[0].weight == 600);
2483 assert(strcmp(server_pool[2].hostname, "10.0.1.3") == 0);
2484 assert(server_pool[2].port == 11211);
2485 assert(server_pool[2].weight == 200);
2486 assert(strcmp(server_pool[7].hostname, "10.0.1.8") == 0);
2487 assert(server_pool[7].port == 11211);
2488 assert(server_pool[7].weight == 100);
2489
2490 memc->hosts[2].next_retry = time(NULL) + 15;
2491 memc->next_distribution_rebuild= time(NULL) - 1;
2492
2493 for (int x= 0; x < 99; x++)
2494 {
2495 uint32_t server_idx = memcached_generate_hash(memc, test_cases[x].key, strlen(test_cases[x].key));
2496 assert(server_idx != 2);
2497 }
2498
2499 /* and re-added when it's back. */
2500 memc->hosts[2].next_retry = time(NULL) - 1;
2501 memc->next_distribution_rebuild= time(NULL) - 1;
2502 run_distribution(memc);
2503 for (int x= 0; x < 99; x++)
2504 {
2505 uint32_t server_idx = memcached_generate_hash(memc, test_cases[x].key, strlen(test_cases[x].key));
2506 char *hostname = memc->hosts[server_idx].hostname;
2507 assert(strcmp(hostname, test_cases[x].server) == 0);
2508 }
2509
2510 memcached_server_list_free(server_pool);
2511 memcached_free(memc);
2512
2513 return TEST_SUCCESS;
2514 }
2515
2516 static test_return result_static(memcached_st *memc)
2517 {
2518 memcached_result_st result;
2519 memcached_result_st *result_ptr;
2520
2521 result_ptr= memcached_result_create(memc, &result);
2522 assert(result.is_allocated == false);
2523 assert(result_ptr);
2524 memcached_result_free(&result);
2525
2526 return 0;
2527 }
2528
2529 static test_return result_alloc(memcached_st *memc)
2530 {
2531 memcached_result_st *result;
2532
2533 result= memcached_result_create(memc, NULL);
2534 assert(result);
2535 memcached_result_free(result);
2536
2537 return 0;
2538 }
2539
2540 static test_return string_static_null(memcached_st *memc)
2541 {
2542 memcached_string_st string;
2543 memcached_string_st *string_ptr;
2544
2545 string_ptr= memcached_string_create(memc, &string, 0);
2546 assert(string.is_allocated == false);
2547 assert(string_ptr);
2548 memcached_string_free(&string);
2549
2550 return 0;
2551 }
2552
2553 static test_return string_alloc_null(memcached_st *memc)
2554 {
2555 memcached_string_st *string;
2556
2557 string= memcached_string_create(memc, NULL, 0);
2558 assert(string);
2559 memcached_string_free(string);
2560
2561 return 0;
2562 }
2563
2564 static test_return string_alloc_with_size(memcached_st *memc)
2565 {
2566 memcached_string_st *string;
2567
2568 string= memcached_string_create(memc, NULL, 1024);
2569 assert(string);
2570 memcached_string_free(string);
2571
2572 return 0;
2573 }
2574
2575 static test_return string_alloc_with_size_toobig(memcached_st *memc)
2576 {
2577 memcached_string_st *string;
2578
2579 string= memcached_string_create(memc, NULL, SIZE_MAX);
2580 assert(string == NULL);
2581
2582 return 0;
2583 }
2584
2585 static test_return string_alloc_append(memcached_st *memc)
2586 {
2587 unsigned int x;
2588 char buffer[SMALL_STRING_LEN];
2589 memcached_string_st *string;
2590
2591 /* Ring the bell! */
2592 memset(buffer, 6, SMALL_STRING_LEN);
2593
2594 string= memcached_string_create(memc, NULL, 100);
2595 assert(string);
2596
2597 for (x= 0; x < 1024; x++)
2598 {
2599 memcached_return rc;
2600 rc= memcached_string_append(string, buffer, SMALL_STRING_LEN);
2601 assert(rc == MEMCACHED_SUCCESS);
2602 }
2603 memcached_string_free(string);
2604
2605 return 0;
2606 }
2607
2608 static test_return string_alloc_append_toobig(memcached_st *memc)
2609 {
2610 memcached_return rc;
2611 unsigned int x;
2612 char buffer[SMALL_STRING_LEN];
2613 memcached_string_st *string;
2614
2615 /* Ring the bell! */
2616 memset(buffer, 6, SMALL_STRING_LEN);
2617
2618 string= memcached_string_create(memc, NULL, 100);
2619 assert(string);
2620
2621 for (x= 0; x < 1024; x++)
2622 {
2623 rc= memcached_string_append(string, buffer, SMALL_STRING_LEN);
2624 assert(rc == MEMCACHED_SUCCESS);
2625 }
2626 rc= memcached_string_append(string, buffer, SIZE_MAX);
2627 assert(rc == MEMCACHED_MEMORY_ALLOCATION_FAILURE);
2628 memcached_string_free(string);
2629
2630 return 0;
2631 }
2632
2633 static test_return cleanup_pairs(memcached_st *memc __attribute__((unused)))
2634 {
2635 pairs_free(global_pairs);
2636
2637 return 0;
2638 }
2639
2640 static test_return generate_pairs(memcached_st *memc __attribute__((unused)))
2641 {
2642 unsigned long long x;
2643 global_pairs= pairs_generate(GLOBAL_COUNT, 400);
2644 global_count= GLOBAL_COUNT;
2645
2646 for (x= 0; x < global_count; x++)
2647 {
2648 global_keys[x]= global_pairs[x].key;
2649 global_keys_length[x]= global_pairs[x].key_length;
2650 }
2651
2652 return 0;
2653 }
2654
2655 static test_return generate_large_pairs(memcached_st *memc __attribute__((unused)))
2656 {
2657 unsigned long long x;
2658 global_pairs= pairs_generate(GLOBAL2_COUNT, MEMCACHED_MAX_BUFFER+10);
2659 global_count= GLOBAL2_COUNT;
2660
2661 for (x= 0; x < global_count; x++)
2662 {
2663 global_keys[x]= global_pairs[x].key;
2664 global_keys_length[x]= global_pairs[x].key_length;
2665 }
2666
2667 return 0;
2668 }
2669
2670 static test_return generate_data(memcached_st *memc)
2671 {
2672 execute_set(memc, global_pairs, global_count);
2673
2674 return 0;
2675 }
2676
2677 static test_return generate_data_with_stats(memcached_st *memc)
2678 {
2679 memcached_stat_st *stat_p;
2680 memcached_return rc;
2681 uint32_t host_index= 0;
2682 execute_set(memc, global_pairs, global_count);
2683
2684 //TODO: hosts used size stats
2685 stat_p= memcached_stat(memc, NULL, &rc);
2686 assert(stat_p);
2687
2688 for (host_index= 0; host_index < SERVERS_TO_CREATE; host_index++)
2689 {
2690 /* This test was changes so that "make test" would work properlly */
2691 #ifdef DEBUG
2692 printf("\nserver %u|%s|%u bytes: %llu\n", host_index, (memc->hosts)[host_index].hostname, (memc->hosts)[host_index].port, (unsigned long long)(stat_p + host_index)->bytes);
2693 #endif
2694 assert((unsigned long long)(stat_p + host_index)->bytes);
2695 }
2696
2697 memcached_stat_free(NULL, stat_p);
2698
2699 return 0;
2700 }
2701 static test_return generate_buffer_data(memcached_st *memc)
2702 {
2703 int latch= 0;
2704
2705 latch= 1;
2706 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_BUFFER_REQUESTS, latch);
2707 generate_data(memc);
2708
2709 return 0;
2710 }
2711
2712 static test_return get_read_count(memcached_st *memc)
2713 {
2714 unsigned int x;
2715 memcached_return rc;
2716 memcached_st *clone;
2717
2718 clone= memcached_clone(NULL, memc);
2719 assert(clone);
2720
2721 memcached_server_add_with_weight(clone, "localhost", 6666, 0);
2722
2723 {
2724 char *return_value;
2725 size_t return_value_length;
2726 uint32_t flags;
2727 uint32_t count;
2728
2729 for (x= count= 0; x < global_count; x++)
2730 {
2731 return_value= memcached_get(clone, global_keys[x], global_keys_length[x],
2732 &return_value_length, &flags, &rc);
2733 if (rc == MEMCACHED_SUCCESS)
2734 {
2735 count++;
2736 if (return_value)
2737 free(return_value);
2738 }
2739 }
2740 fprintf(stderr, "\t%u -> %u", global_count, count);
2741 }
2742
2743 memcached_free(clone);
2744
2745 return 0;
2746 }
2747
2748 static test_return get_read(memcached_st *memc)
2749 {
2750 unsigned int x;
2751 memcached_return rc;
2752
2753 {
2754 char *return_value;
2755 size_t return_value_length;
2756 uint32_t flags;
2757
2758 for (x= 0; x < global_count; x++)
2759 {
2760 return_value= memcached_get(memc, global_keys[x], global_keys_length[x],
2761 &return_value_length, &flags, &rc);
2762 /*
2763 assert(return_value);
2764 assert(rc == MEMCACHED_SUCCESS);
2765 */
2766 if (rc == MEMCACHED_SUCCESS && return_value)
2767 free(return_value);
2768 }
2769 }
2770
2771 return 0;
2772 }
2773
2774 static test_return mget_read(memcached_st *memc)
2775 {
2776 memcached_return rc;
2777
2778 rc= memcached_mget(memc, global_keys, global_keys_length, global_count);
2779 assert(rc == MEMCACHED_SUCCESS);
2780 /* Turn this into a help function */
2781 {
2782 char return_key[MEMCACHED_MAX_KEY];
2783 size_t return_key_length;
2784 char *return_value;
2785 size_t return_value_length;
2786 uint32_t flags;
2787
2788 while ((return_value= memcached_fetch(memc, return_key, &return_key_length,
2789 &return_value_length, &flags, &rc)))
2790 {
2791 assert(return_value);
2792 assert(rc == MEMCACHED_SUCCESS);
2793 free(return_value);
2794 }
2795 }
2796
2797 return 0;
2798 }
2799
2800 static test_return mget_read_result(memcached_st *memc)
2801 {
2802 memcached_return rc;
2803
2804 rc= memcached_mget(memc, global_keys, global_keys_length, global_count);
2805 assert(rc == MEMCACHED_SUCCESS);
2806 /* Turn this into a help function */
2807 {
2808 memcached_result_st results_obj;
2809 memcached_result_st *results;
2810
2811 results= memcached_result_create(memc, &results_obj);
2812
2813 while ((results= memcached_fetch_result(memc, &results_obj, &rc)))
2814 {
2815 assert(results);
2816 assert(rc == MEMCACHED_SUCCESS);
2817 }
2818
2819 memcached_result_free(&results_obj);
2820 }
2821
2822 return 0;
2823 }
2824
2825 static test_return mget_read_function(memcached_st *memc)
2826 {
2827 memcached_return rc;
2828 unsigned int counter;
2829 memcached_execute_function callbacks[1];
2830
2831 rc= memcached_mget(memc, global_keys, global_keys_length, global_count);
2832 assert(rc == MEMCACHED_SUCCESS);
2833
2834 callbacks[0]= &callback_counter;
2835 counter= 0;
2836 rc= memcached_fetch_execute(memc, callbacks, (void *)&counter, 1);
2837
2838 return 0;
2839 }
2840
2841 static test_return delete_generate(memcached_st *memc)
2842 {
2843 unsigned int x;
2844
2845 for (x= 0; x < global_count; x++)
2846 {
2847 (void)memcached_delete(memc, global_keys[x], global_keys_length[x], (time_t)0);
2848 }
2849
2850 return 0;
2851 }
2852
2853 static test_return delete_buffer_generate(memcached_st *memc)
2854 {
2855 int latch= 0;
2856 unsigned int x;
2857
2858 latch= 1;
2859 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_BUFFER_REQUESTS, latch);
2860
2861 for (x= 0; x < global_count; x++)
2862 {
2863 (void)memcached_delete(memc, global_keys[x], global_keys_length[x], (time_t)0);
2864 }
2865
2866 return 0;
2867 }
2868
2869 static test_return add_host_test1(memcached_st *memc)
2870 {
2871 unsigned int x;
2872 memcached_return rc;
2873 char servername[]= "0.example.com";
2874 memcached_server_st *servers;
2875
2876 servers= memcached_server_list_append_with_weight(NULL, servername, 400, 0, &rc);
2877 assert(servers);
2878 assert(1 == memcached_server_list_count(servers));
2879
2880 for (x= 2; x < 20; x++)
2881 {
2882 char buffer[SMALL_STRING_LEN];
2883
2884 snprintf(buffer, SMALL_STRING_LEN, "%u.example.com", 400+x);
2885 servers= memcached_server_list_append_with_weight(servers, buffer, 401, 0,
2886 &rc);
2887 assert(rc == MEMCACHED_SUCCESS);
2888 assert(x == memcached_server_list_count(servers));
2889 }
2890
2891 rc= memcached_server_push(memc, servers);
2892 assert(rc == MEMCACHED_SUCCESS);
2893 rc= memcached_server_push(memc, servers);
2894 assert(rc == MEMCACHED_SUCCESS);
2895
2896 memcached_server_list_free(servers);
2897
2898 return 0;
2899 }
2900
2901 static memcached_return pre_nonblock(memcached_st *memc)
2902 {
2903 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_NO_BLOCK, 0);
2904
2905 return MEMCACHED_SUCCESS;
2906 }
2907
2908 static memcached_return pre_nonblock_binary(memcached_st *memc)
2909 {
2910 memcached_return rc= MEMCACHED_FAILURE;
2911 memcached_st *clone;
2912
2913 clone= memcached_clone(NULL, memc);
2914 assert(clone);
2915 // The memcached_version needs to be done on a clone, because the server
2916 // will not toggle protocol on an connection.
2917 memcached_version(clone);
2918
2919 if (clone->hosts[0].major_version >= 1 && clone->hosts[0].minor_version > 2)
2920 {
2921 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_NO_BLOCK, 0);
2922 rc = memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_BINARY_PROTOCOL, 1);
2923 assert(rc == MEMCACHED_SUCCESS);
2924 assert(memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_BINARY_PROTOCOL) == 1);
2925 }
2926
2927 memcached_free(clone);
2928 return rc;
2929 }
2930
2931 static memcached_return pre_murmur(memcached_st *memc)
2932 {
2933 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_HASH, (uint64_t)MEMCACHED_HASH_MURMUR);
2934
2935 return MEMCACHED_SUCCESS;
2936 }
2937
2938 static memcached_return pre_jenkins(memcached_st *memc)
2939 {
2940 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_HASH, (uint64_t)MEMCACHED_HASH_JENKINS);
2941
2942 return MEMCACHED_SUCCESS;
2943 }
2944
2945
2946 static memcached_return pre_md5(memcached_st *memc)
2947 {
2948 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_HASH, (uint64_t)MEMCACHED_HASH_MD5);
2949
2950 return MEMCACHED_SUCCESS;
2951 }
2952
2953 static memcached_return pre_crc(memcached_st *memc)
2954 {
2955 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_HASH, (uint64_t)MEMCACHED_HASH_CRC);
2956
2957 return MEMCACHED_SUCCESS;
2958 }
2959
2960 static memcached_return pre_hsieh(memcached_st *memc)
2961 {
2962 #ifdef HAVE_HSIEH_HASH
2963 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_HASH, (uint64_t)MEMCACHED_HASH_HSIEH);
2964 return MEMCACHED_SUCCESS;
2965 #else
2966 (void) memc;
2967 return MEMCACHED_FAILURE;
2968 #endif
2969 }
2970
2971 static memcached_return pre_hash_fnv1_64(memcached_st *memc)
2972 {
2973 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_HASH, (uint64_t)MEMCACHED_HASH_FNV1_64);
2974
2975 return MEMCACHED_SUCCESS;
2976 }
2977
2978 static memcached_return pre_hash_fnv1a_64(memcached_st *memc)
2979 {
2980 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_HASH, (uint64_t)MEMCACHED_HASH_FNV1A_64);
2981
2982 return MEMCACHED_SUCCESS;
2983 }
2984
2985 static memcached_return pre_hash_fnv1_32(memcached_st *memc)
2986 {
2987 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_HASH, (uint64_t)MEMCACHED_HASH_FNV1_32);
2988
2989 return MEMCACHED_SUCCESS;
2990 }
2991
2992 static memcached_return pre_hash_fnv1a_32(memcached_st *memc)
2993 {
2994 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_HASH, (uint64_t)MEMCACHED_HASH_FNV1A_32);
2995
2996 return MEMCACHED_SUCCESS;
2997 }
2998
2999 static memcached_return pre_behavior_ketama(memcached_st *memc)
3000 {
3001 memcached_return rc;
3002 uint64_t value;
3003
3004 rc= memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_KETAMA, 1);
3005 assert(rc == MEMCACHED_SUCCESS);
3006
3007 value= memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_KETAMA);
3008 assert(value == 1);
3009
3010 return MEMCACHED_SUCCESS;
3011 }
3012
3013 static memcached_return pre_behavior_ketama_weighted(memcached_st *memc)
3014 {
3015 memcached_return rc;
3016 uint64_t value;
3017
3018 rc= memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_KETAMA_WEIGHTED, 1);
3019 assert(rc == MEMCACHED_SUCCESS);
3020
3021 value= memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_KETAMA_WEIGHTED);
3022 assert(value == 1);
3023
3024 rc= memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_KETAMA_HASH, MEMCACHED_HASH_MD5);
3025 assert(rc == MEMCACHED_SUCCESS);
3026
3027 value= memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_KETAMA_HASH);
3028 assert(value == MEMCACHED_HASH_MD5);
3029 return MEMCACHED_SUCCESS;
3030 }
3031
3032 static memcached_return pre_binary(memcached_st *memc)
3033 {
3034 memcached_return rc= MEMCACHED_FAILURE;
3035 memcached_st *clone;
3036
3037 clone= memcached_clone(NULL, memc);
3038 assert(clone);
3039 // The memcached_version needs to be done on a clone, because the server
3040 // will not toggle protocol on an connection.
3041 memcached_version(clone);
3042
3043 if (clone->hosts[0].major_version >= 1 && clone->hosts[0].minor_version > 2)
3044 {
3045 rc = memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_BINARY_PROTOCOL, 1);
3046 assert(rc == MEMCACHED_SUCCESS);
3047 assert(memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_BINARY_PROTOCOL) == 1);
3048 }
3049
3050 memcached_free(clone);
3051 return rc;
3052 }
3053
3054 static memcached_return pre_replication(memcached_st *memc)
3055 {
3056 memcached_return rc= MEMCACHED_FAILURE;
3057 if (pre_binary(memc) == MEMCACHED_SUCCESS)
3058 {
3059 /*
3060 * Make sure that we store the item on all servers
3061 * (master + replicas == number of servers)
3062 */
3063 rc= memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_NUMBER_OF_REPLICAS,
3064 memc->number_of_hosts - 1);
3065 assert(rc == MEMCACHED_SUCCESS);
3066 assert(memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_NUMBER_OF_REPLICAS) == memc->number_of_hosts - 1);
3067 }
3068
3069 return rc;
3070 }
3071
3072 static void my_free(memcached_st *ptr __attribute__((unused)), void *mem)
3073 {
3074 free(mem);
3075 }
3076
3077 static void *my_malloc(memcached_st *ptr __attribute__((unused)), const size_t size)
3078 {
3079 void *ret= malloc(size);
3080 if (ret != NULL)
3081 memset(ret, 0xff, size);
3082
3083 return ret;
3084 }
3085
3086 static void *my_realloc(memcached_st *ptr __attribute__((unused)), void *mem, const size_t size)
3087 {
3088 return realloc(mem, size);
3089 }
3090
3091 static void *my_calloc(memcached_st *ptr __attribute__((unused)), size_t nelem, const size_t size)
3092 {
3093 return calloc(nelem, size);
3094 }
3095
3096 static memcached_return set_prefix(memcached_st *memc)
3097 {
3098 memcached_return rc;
3099 const char *key= "mine";
3100 char *value;
3101
3102 /* Make sure be default none exists */
3103 value= memcached_callback_get(memc, MEMCACHED_CALLBACK_PREFIX_KEY, &rc);
3104 assert(rc == MEMCACHED_FAILURE);
3105
3106 /* Test a clean set */
3107 rc= memcached_callback_set(memc, MEMCACHED_CALLBACK_PREFIX_KEY, (void *)key);
3108 assert(rc == MEMCACHED_SUCCESS);
3109
3110 value= memcached_callback_get(memc, MEMCACHED_CALLBACK_PREFIX_KEY, &rc);
3111 assert(memcmp(value, key, 4) == 0);
3112 assert(rc == MEMCACHED_SUCCESS);
3113
3114 /* Test that we can turn it off */
3115 rc= memcached_callback_set(memc, MEMCACHED_CALLBACK_PREFIX_KEY, NULL);
3116 assert(rc == MEMCACHED_SUCCESS);
3117
3118 value= memcached_callback_get(memc, MEMCACHED_CALLBACK_PREFIX_KEY, &rc);
3119 assert(rc == MEMCACHED_FAILURE);
3120
3121 /* Now setup for main test */
3122 rc= memcached_callback_set(memc, MEMCACHED_CALLBACK_PREFIX_KEY, (void *)key);
3123 assert(rc == MEMCACHED_SUCCESS);
3124
3125 value= memcached_callback_get(memc, MEMCACHED_CALLBACK_PREFIX_KEY, &rc);
3126 assert(rc == MEMCACHED_SUCCESS);
3127 assert(memcmp(value, key, 4) == 0);
3128
3129 /* Set to Zero, and then Set to something too large */
3130 {
3131 char *long_key;
3132 rc= memcached_callback_set(memc, MEMCACHED_CALLBACK_PREFIX_KEY, NULL);
3133 assert(rc == MEMCACHED_SUCCESS);
3134
3135 value= memcached_callback_get(memc, MEMCACHED_CALLBACK_PREFIX_KEY, &rc);
3136 assert(rc == MEMCACHED_FAILURE);
3137 assert(value == NULL);
3138
3139 /* Test a long key for failure */
3140 /* TODO, extend test to determine based on setting, what result should be */
3141 long_key= "Thisismorethentheallottednumberofcharacters";
3142 rc= memcached_callback_set(memc, MEMCACHED_CALLBACK_PREFIX_KEY, long_key);
3143 //assert(rc == MEMCACHED_BAD_KEY_PROVIDED);
3144 assert(rc == MEMCACHED_SUCCESS);
3145
3146 /* Now test a key with spaces (which will fail from long key, since bad key is not set) */
3147 long_key= "This is more then the allotted number of characters";
3148 rc= memcached_callback_set(memc, MEMCACHED_CALLBACK_PREFIX_KEY, long_key);
3149 assert(rc == MEMCACHED_BAD_KEY_PROVIDED);
3150
3151 /* Test for a bad prefix, but with a short key */
3152 rc= memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_VERIFY_KEY, 1);
3153 assert(rc == MEMCACHED_SUCCESS);
3154
3155 long_key= "dog cat";
3156 rc= memcached_callback_set(memc, MEMCACHED_CALLBACK_PREFIX_KEY, long_key);
3157 assert(rc == MEMCACHED_BAD_KEY_PROVIDED);
3158 }
3159
3160 return MEMCACHED_SUCCESS;
3161 }
3162
3163 static memcached_return deprecated_set_memory_alloc(memcached_st *memc)
3164 {
3165 void *test_ptr= NULL;
3166 void *cb_ptr= NULL;
3167 {
3168 memcached_malloc_function malloc_cb=
3169 (memcached_malloc_function)my_malloc;
3170 cb_ptr= *(void **)&malloc_cb;
3171 memcached_return rc;
3172
3173 rc= memcached_callback_set(memc, MEMCACHED_CALLBACK_MALLOC_FUNCTION, cb_ptr);
3174 assert(rc == MEMCACHED_SUCCESS);
3175 test_ptr= memcached_callback_get(memc, MEMCACHED_CALLBACK_MALLOC_FUNCTION, &rc);
3176 assert(rc == MEMCACHED_SUCCESS);
3177 assert(test_ptr == cb_ptr);
3178 }
3179
3180 {
3181 memcached_realloc_function realloc_cb=
3182 (memcached_realloc_function)my_realloc;
3183 cb_ptr= *(void **)&realloc_cb;
3184 memcached_return rc;
3185
3186 rc= memcached_callback_set(memc, MEMCACHED_CALLBACK_REALLOC_FUNCTION, cb_ptr);
3187 assert(rc == MEMCACHED_SUCCESS);
3188 test_ptr= memcached_callback_get(memc, MEMCACHED_CALLBACK_REALLOC_FUNCTION, &rc);
3189 assert(rc == MEMCACHED_SUCCESS);
3190 assert(test_ptr == cb_ptr);
3191 }
3192
3193 {
3194 memcached_free_function free_cb=
3195 (memcached_free_function)my_free;
3196 cb_ptr= *(void **)&free_cb;
3197 memcached_return rc;
3198
3199 rc= memcached_callback_set(memc, MEMCACHED_CALLBACK_FREE_FUNCTION, cb_ptr);
3200 assert(rc == MEMCACHED_SUCCESS);
3201 test_ptr= memcached_callback_get(memc, MEMCACHED_CALLBACK_FREE_FUNCTION, &rc);
3202 assert(rc == MEMCACHED_SUCCESS);
3203 assert(test_ptr == cb_ptr);
3204 }
3205 return MEMCACHED_SUCCESS;
3206 }
3207
3208 static memcached_return set_memory_alloc(memcached_st *memc)
3209 {
3210 memcached_return rc;
3211 rc= memcached_set_memory_allocators(memc, NULL, my_free,
3212 my_realloc, my_calloc);
3213 assert(rc == MEMCACHED_FAILURE);
3214
3215 rc= memcached_set_memory_allocators(memc, my_malloc, my_free,
3216 my_realloc, my_calloc);
3217
3218 memcached_malloc_function mem_malloc;
3219 memcached_free_function mem_free;
3220 memcached_realloc_function mem_realloc;
3221 memcached_calloc_function mem_calloc;
3222 memcached_get_memory_allocators(memc, &mem_malloc, &mem_free,
3223 &mem_realloc, &mem_calloc);
3224
3225 assert(mem_malloc == my_malloc);
3226 assert(mem_realloc == my_realloc);
3227 assert(mem_calloc == my_calloc);
3228 assert(mem_free == my_free);
3229
3230 return MEMCACHED_SUCCESS;
3231 }
3232
3233 static memcached_return enable_consistent(memcached_st *memc)
3234 {
3235 memcached_server_distribution value= MEMCACHED_DISTRIBUTION_CONSISTENT;
3236 memcached_hash hash;
3237 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_DISTRIBUTION, value);
3238 if (pre_hsieh(memc) != MEMCACHED_SUCCESS)
3239 return MEMCACHED_FAILURE;
3240
3241 value= (memcached_server_distribution)memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_DISTRIBUTION);
3242 assert(value == MEMCACHED_DISTRIBUTION_CONSISTENT);
3243
3244 hash= (memcached_hash)memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_HASH);
3245 assert(hash == MEMCACHED_HASH_HSIEH);
3246
3247
3248 return MEMCACHED_SUCCESS;
3249 }
3250
3251 static memcached_return enable_cas(memcached_st *memc)
3252 {
3253 unsigned int set= 1;
3254
3255 memcached_version(memc);
3256
3257 if ((memc->hosts[0].major_version >= 1 && (memc->hosts[0].minor_version == 2 && memc->hosts[0].micro_version >= 4))
3258 || memc->hosts[0].minor_version > 2)
3259 {
3260 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_SUPPORT_CAS, set);
3261
3262 return MEMCACHED_SUCCESS;
3263 }
3264
3265 return MEMCACHED_FAILURE;
3266 }
3267
3268 static memcached_return check_for_1_2_3(memcached_st *memc)
3269 {
3270 memcached_version(memc);
3271
3272 if ((memc->hosts[0].major_version >= 1 && (memc->hosts[0].minor_version == 2 && memc->hosts[0].micro_version >= 4))
3273 || memc->hosts[0].minor_version > 2)
3274 return MEMCACHED_SUCCESS;
3275
3276 return MEMCACHED_FAILURE;
3277 }
3278
3279 static memcached_return pre_unix_socket(memcached_st *memc)
3280 {
3281 memcached_return rc;
3282 struct stat buf;
3283
3284 memcached_server_list_free(memc->hosts);
3285 memc->hosts= NULL;
3286 memc->number_of_hosts= 0;
3287
3288 if (stat("/tmp/memcached.socket", &buf))
3289 return MEMCACHED_FAILURE;
3290
3291 rc= memcached_server_add_unix_socket_with_weight(memc, "/tmp/memcached.socket", 0);
3292
3293 return rc;
3294 }
3295
3296 static memcached_return pre_nodelay(memcached_st *memc)
3297 {
3298 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_NO_BLOCK, 0);
3299 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_TCP_NODELAY, 0);
3300
3301 return MEMCACHED_SUCCESS;
3302 }
3303
3304 static memcached_return pre_settimer(memcached_st *memc)
3305 {
3306 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_SND_TIMEOUT, 1000);
3307 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_RCV_TIMEOUT, 1000);
3308
3309 return MEMCACHED_SUCCESS;
3310 }
3311
3312 static memcached_return poll_timeout(memcached_st *memc)
3313 {
3314 int32_t timeout;
3315
3316 timeout= 100;
3317
3318 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_POLL_TIMEOUT, timeout);
3319
3320 timeout= (int32_t)memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_POLL_TIMEOUT);
3321
3322 assert(timeout == 100);
3323
3324 return MEMCACHED_SUCCESS;
3325 }
3326
3327 static test_return noreply_test(memcached_st *memc)
3328 {
3329 memcached_return ret;
3330 ret= memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_NOREPLY, 1);
3331 assert(ret == MEMCACHED_SUCCESS);
3332 ret= memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_BUFFER_REQUESTS, 1);
3333 assert(ret == MEMCACHED_SUCCESS);
3334 ret= memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_SUPPORT_CAS, 1);
3335 assert(ret == MEMCACHED_SUCCESS);
3336 assert(memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_NOREPLY) == 1);
3337 assert(memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_BUFFER_REQUESTS) == 1);
3338 assert(memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_SUPPORT_CAS) == 1);
3339
3340 for (int count=0; count < 5; ++count)
3341 {
3342 for (int x=0; x < 100; ++x)
3343 {
3344 char key[10];
3345 size_t len= sprintf(key, "%d", x);
3346 switch (count)
3347 {
3348 case 0:
3349 ret=memcached_add(memc, key, len, key, len, 0, 0);
3350 break;
3351 case 1:
3352 ret=memcached_replace(memc, key, len, key, len, 0, 0);
3353 break;
3354 case 2:
3355 ret=memcached_set(memc, key, len, key, len, 0, 0);
3356 break;
3357 case 3:
3358 ret=memcached_append(memc, key, len, key, len, 0, 0);
3359 break;
3360 case 4:
3361 ret=memcached_prepend(memc, key, len, key, len, 0, 0);
3362 break;
3363 }
3364 assert(ret == MEMCACHED_SUCCESS || ret == MEMCACHED_BUFFERED);
3365 }
3366
3367 /*
3368 ** NOTE: Don't ever do this in your code! this is not a supported use of the
3369 ** API and is _ONLY_ done this way to verify that the library works the
3370 ** way it is supposed to do!!!!
3371 */
3372 int no_msg=0;
3373 for (uint32_t x=0; x < memc->number_of_hosts; ++x)
3374 no_msg+=memc->hosts[x].cursor_active;
3375
3376 assert(no_msg == 0);
3377 assert(memcached_flush_buffers(memc) == MEMCACHED_SUCCESS);
3378
3379 /*
3380 ** Now validate that all items was set properly!
3381 */
3382 for (int x=0; x < 100; ++x)
3383 {
3384 char key[10];
3385 size_t len= sprintf(key, "%d", x);
3386 size_t length;
3387 uint32_t flags;
3388 char* value=memcached_get(memc, key, strlen(key),
3389 &length, &flags, &ret);
3390 assert(ret == MEMCACHED_SUCCESS && value != NULL);
3391 switch (count)
3392 {
3393 case 0: /* FALLTHROUGH */
3394 case 1: /* FALLTHROUGH */
3395 case 2:
3396 assert(strncmp(value, key, len) == 0);
3397 assert(len == length);
3398 break;
3399 case 3:
3400 assert(length == len * 2);
3401 break;
3402 case 4:
3403 assert(length == len * 3);
3404 break;
3405 }
3406 free(value);
3407 }
3408 }
3409
3410 /* Try setting an illegal cas value (should not return an error to
3411 * the caller (because we don't expect a return message from the server)
3412 */
3413 char* keys[]= {"0"};
3414 size_t lengths[]= {1};
3415 size_t length;
3416 uint32_t flags;
3417 memcached_result_st results_obj;
3418 memcached_result_st *results;
3419 ret= memcached_mget(memc, keys, lengths, 1);
3420 assert(ret == MEMCACHED_SUCCESS);
3421
3422 results= memcached_result_create(memc, &results_obj);
3423 assert(results);
3424 results= memcached_fetch_result(memc, &results_obj, &ret);
3425 assert(results);
3426 assert(ret == MEMCACHED_SUCCESS);
3427 uint64_t cas= memcached_result_cas(results);
3428 memcached_result_free(&results_obj);
3429
3430 ret= memcached_cas(memc, keys[0], lengths[0], keys[0], lengths[0], 0, 0, cas);
3431 assert(ret == MEMCACHED_SUCCESS);
3432
3433 /*
3434 * The item will have a new cas value, so try to set it again with the old
3435 * value. This should fail!
3436 */
3437 ret= memcached_cas(memc, keys[0], lengths[0], keys[0], lengths[0], 0, 0, cas);
3438 assert(ret == MEMCACHED_SUCCESS);
3439 assert(memcached_flush_buffers(memc) == MEMCACHED_SUCCESS);
3440 char* value=memcached_get(memc, keys[0], lengths[0], &length, &flags, &ret);
3441 assert(ret == MEMCACHED_SUCCESS && value != NULL);
3442 free(value);
3443
3444 return TEST_SUCCESS;
3445 }
3446
3447 static test_return analyzer_test(memcached_st *memc)
3448 {
3449 memcached_return rc;
3450 memcached_stat_st *stat;
3451 memcached_analysis_st *report;
3452
3453 stat= memcached_stat(memc, NULL, &rc);
3454 assert(rc == MEMCACHED_SUCCESS);
3455 assert(stat);
3456
3457 report= memcached_analyze(memc, stat, &rc);
3458 assert(rc == MEMCACHED_SUCCESS);
3459 assert(report);
3460
3461 free(report);
3462 memcached_stat_free(NULL, stat);
3463
3464 return TEST_SUCCESS;
3465 }
3466
3467 /* Count the objects */
3468 static memcached_return callback_dump_counter(memcached_st *ptr __attribute__((unused)),
3469 const char *key __attribute__((unused)),
3470 size_t key_length __attribute__((unused)),
3471 void *context)
3472 {
3473 uint32_t *counter= (uint32_t *)context;
3474
3475 *counter= *counter + 1;
3476
3477 return MEMCACHED_SUCCESS;
3478 }
3479
3480 static test_return dump_test(memcached_st *memc)
3481 {
3482 memcached_return rc;
3483 uint32_t counter= 0;
3484 memcached_dump_func callbacks[1];
3485 test_return main_rc;
3486
3487 callbacks[0]= &callback_dump_counter;
3488
3489 /* No support for Binary protocol yet */
3490 if (memc->flags & MEM_BINARY_PROTOCOL)
3491 return TEST_SUCCESS;
3492
3493 main_rc= set_test3(memc);
3494
3495 assert (main_rc == TEST_SUCCESS);
3496
3497 rc= memcached_dump(memc, callbacks, (void *)&counter, 1);
3498 assert(rc == MEMCACHED_SUCCESS);
3499
3500 /* We may have more then 32 if our previous flush has not completed */
3501 assert(counter >= 32);
3502
3503 return TEST_SUCCESS;
3504 }
3505
3506 #ifdef HAVE_LIBMEMCACHEDUTIL
3507 static void* connection_release(void *arg) {
3508 struct {
3509 memcached_pool_st* pool;
3510 memcached_st* mmc;
3511 } *resource= arg;
3512
3513 usleep(250);
3514 assert(memcached_pool_push(resource->pool, resource->mmc) == MEMCACHED_SUCCESS);
3515 return arg;
3516 }
3517
3518 static test_return connection_pool_test(memcached_st *memc)
3519 {
3520 memcached_pool_st* pool= memcached_pool_create(memc, 5, 10);
3521 assert(pool != NULL);
3522 memcached_st* mmc[10];
3523 memcached_return rc;
3524
3525 for (int x= 0; x < 10; ++x) {
3526 mmc[x]= memcached_pool_pop(pool, false, &rc);
3527 assert(mmc[x] != NULL);
3528 assert(rc == MEMCACHED_SUCCESS);
3529 }
3530
3531 assert(memcached_pool_pop(pool, false, &rc) == NULL);
3532 assert(rc == MEMCACHED_SUCCESS);
3533
3534 pthread_t tid;
3535 struct {
3536 memcached_pool_st* pool;
3537 memcached_st* mmc;
3538 } item= { .pool = pool, .mmc = mmc[9] };
3539 pthread_create(&tid, NULL, connection_release, &item);
3540 mmc[9]= memcached_pool_pop(pool, true, &rc);
3541 assert(rc == MEMCACHED_SUCCESS);
3542 pthread_join(tid, NULL);
3543 assert(mmc[9] == item.mmc);
3544 const char *key= "key";
3545 size_t keylen= strlen(key);
3546
3547 // verify that I can do ops with all connections
3548 rc= memcached_set(mmc[0], key, keylen, "0", 1, 0, 0);
3549 assert(rc == MEMCACHED_SUCCESS);
3550
3551 for (unsigned int x= 0; x < 10; ++x) {
3552 uint64_t number_value;
3553 rc= memcached_increment(mmc[x], key, keylen, 1, &number_value);
3554 assert(rc == MEMCACHED_SUCCESS);
3555 assert(number_value == (x+1));
3556 }
3557
3558 // Release them..
3559 for (int x= 0; x < 10; ++x)
3560 assert(memcached_pool_push(pool, mmc[x]) == MEMCACHED_SUCCESS);
3561
3562 assert(memcached_pool_destroy(pool) == memc);
3563 return TEST_SUCCESS;
3564 }
3565 #endif
3566
3567 static test_return replication_set_test(memcached_st *memc)
3568 {
3569 memcached_return rc;
3570 memcached_st *clone= memcached_clone(NULL, memc);
3571 memcached_behavior_set(clone, MEMCACHED_BEHAVIOR_NUMBER_OF_REPLICAS, 0);
3572
3573 rc= memcached_set(memc, "bubba", 5, "0", 1, 0, 0);
3574 assert(rc == MEMCACHED_SUCCESS);
3575
3576 /*
3577 ** "bubba" should now be stored on all of our servers. We don't have an
3578 ** easy to use API to address each individual server, so I'll just iterate
3579 ** through a bunch of "master keys" and I should most likely hit all of the
3580 ** servers...
3581 */
3582 for (int x= 'a'; x <= 'z'; ++x)
3583 {
3584 char key[2]= { [0]= (char)x };
3585 size_t len;
3586 uint32_t flags;
3587 char *val= memcached_get_by_key(clone, key, 1, "bubba", 5,
3588 &len, &flags, &rc);
3589 assert(rc == MEMCACHED_SUCCESS);
3590 assert(val != NULL);
3591 free(val);
3592 }
3593
3594 memcached_free(clone);
3595
3596 return TEST_SUCCESS;
3597 }
3598
3599 static test_return replication_get_test(memcached_st *memc)
3600 {
3601 memcached_return rc;
3602
3603 /*
3604 * Don't do the following in your code. I am abusing the internal details
3605 * within the library, and this is not a supported interface.
3606 * This is to verify correct behavior in the library
3607 */
3608 for (int host= 0; host < memc->number_of_hosts; ++host) {
3609 memcached_st *clone= memcached_clone(NULL, memc);
3610 clone->hosts[host].port= 0;
3611
3612 for (int x= 'a'; x <= 'z'; ++x)
3613 {
3614 char key[2]= { [0]= (char)x };
3615 size_t len;
3616 uint32_t flags;
3617 char *val= memcached_get_by_key(clone, key, 1, "bubba", 5,
3618 &len, &flags, &rc);
3619 assert(rc == MEMCACHED_SUCCESS);
3620 assert(val != NULL);
3621 free(val);
3622 }
3623
3624 memcached_free(clone);
3625 }
3626
3627 return TEST_SUCCESS;
3628 }
3629
3630 static test_return replication_mget_test(memcached_st *memc)
3631 {
3632 memcached_return rc;
3633 memcached_st *clone= memcached_clone(NULL, memc);
3634 memcached_behavior_set(clone, MEMCACHED_BEHAVIOR_NUMBER_OF_REPLICAS, 0);
3635
3636 char *keys[]= { "bubba", "key1", "key2", "key3" };
3637 size_t len[]= { 5, 4, 4, 4 };
3638
3639 for (int x=0; x< 4; ++x)
3640 {
3641 rc= memcached_set(memc, keys[x], len[x], "0", 1, 0, 0);
3642 assert(rc == MEMCACHED_SUCCESS);
3643 }
3644
3645 /*
3646 * Don't do the following in your code. I am abusing the internal details
3647 * within the library, and this is not a supported interface.
3648 * This is to verify correct behavior in the library
3649 */
3650 memcached_result_st result_obj;
3651 for (int host= 0; host < clone->number_of_hosts; ++host)
3652 {
3653 memcached_st *clone= memcached_clone(NULL, memc);
3654 clone->hosts[host].port= 0;
3655
3656 for (int x= 'a'; x <= 'z'; ++x)
3657 {
3658 char key[2]= { [0]= (char)x };
3659
3660 rc= memcached_mget_by_key(clone, key, 1, keys, len, 4);
3661 assert(rc == MEMCACHED_SUCCESS);
3662
3663 memcached_result_st *results= memcached_result_create(clone, &result_obj);
3664 assert(results);
3665
3666 int hits= 0;
3667 while ((results= memcached_fetch_result(clone, &result_obj, &rc)) != NULL)
3668 {
3669 hits++;
3670 }
3671 assert(hits == 4);
3672 memcached_result_free(&result_obj);
3673 }
3674
3675 memcached_free(clone);
3676 }
3677
3678 return TEST_SUCCESS;
3679 }
3680
3681 static test_return replication_delete_test(memcached_st *memc)
3682 {
3683 memcached_return rc;
3684 memcached_st *clone= memcached_clone(NULL, memc);
3685 /* Delete the items from all of the servers except 1 */
3686 uint64_t repl= memcached_behavior_get(memc,
3687 MEMCACHED_BEHAVIOR_NUMBER_OF_REPLICAS);
3688 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_NUMBER_OF_REPLICAS, --repl);
3689
3690 char *keys[]= { "bubba", "key1", "key2", "key3" };
3691 size_t len[]= { 5, 4, 4, 4 };
3692
3693 for (int x=0; x< 4; ++x)
3694 {
3695 rc= memcached_delete_by_key(memc, keys[0], len[0], keys[x], len[x], 0);
3696 assert(rc == MEMCACHED_SUCCESS);
3697 }
3698
3699 /*
3700 * Don't do the following in your code. I am abusing the internal details
3701 * within the library, and this is not a supported interface.
3702 * This is to verify correct behavior in the library
3703 */
3704 int hash= memcached_generate_hash(memc, keys[0], len[0]);
3705 for (int x= 0; x < (repl + 1); ++x) {
3706 clone->hosts[hash].port= 0;
3707 if (++hash == clone->number_of_hosts)
3708 hash= 0;
3709 }
3710
3711 memcached_result_st result_obj;
3712 for (int host= 0; host < clone->number_of_hosts; ++host)
3713 {
3714 for (int x= 'a'; x <= 'z'; ++x)
3715 {
3716 char key[2]= { [0]= (char)x };
3717
3718 rc= memcached_mget_by_key(clone, key, 1, keys, len, 4);
3719 assert(rc == MEMCACHED_SUCCESS);
3720
3721 memcached_result_st *results= memcached_result_create(clone, &result_obj);
3722 assert(results);
3723
3724 int hits= 0;
3725 while ((results= memcached_fetch_result(clone, &result_obj, &rc)) != NULL)
3726 {
3727 ++hits;
3728 }
3729 assert(hits == 4);
3730 memcached_result_free(&result_obj);
3731 }
3732 }
3733 memcached_free(clone);
3734
3735 return TEST_SUCCESS;
3736 }
3737
3738 static void increment_request_id(uint16_t *id)
3739 {
3740 (*id)++;
3741 if ((*id & UDP_REQUEST_ID_THREAD_MASK) != 0)
3742 *id= 0;
3743 }
3744
3745 static uint16_t *get_udp_request_ids(memcached_st *memc)
3746 {
3747 uint16_t *ids= malloc(sizeof(uint16_t) * memc->number_of_hosts);
3748 assert(ids != NULL);
3749 unsigned int x;
3750
3751 for (x= 0; x < memc->number_of_hosts; x++)
3752 ids[x]= get_udp_datagram_request_id((struct udp_datagram_header_st *) memc->hosts[x].write_buffer);
3753
3754 return ids;
3755 }
3756
3757 static test_return post_udp_op_check(memcached_st *memc, uint16_t *expected_req_ids)
3758 {
3759 unsigned int x;
3760 memcached_server_st *cur_server = memc->hosts;
3761 uint16_t *cur_req_ids = get_udp_request_ids(memc);
3762
3763 for (x= 0; x < memc->number_of_hosts; x++)
3764 {
3765 assert(cur_server[x].cursor_active == 0);
3766 assert(cur_req_ids[x] == expected_req_ids[x]);
3767 }
3768 free(expected_req_ids);
3769 free(cur_req_ids);
3770
3771 return TEST_SUCCESS;
3772 }
3773
3774 /*
3775 ** There is a little bit of a hack here, instead of removing
3776 ** the servers, I just set num host to 0 and them add then new udp servers
3777 **/
3778 static memcached_return init_udp(memcached_st *memc)
3779 {
3780 memcached_version(memc);
3781 /* For the time being, only support udp test for >= 1.2.6 && < 1.3 */
3782 if (memc->hosts[0].major_version != 1 || memc->hosts[0].minor_version != 2
3783 || memc->hosts[0].micro_version < 6)
3784 return MEMCACHED_FAILURE;
3785
3786 uint32_t num_hosts= memc->number_of_hosts;
3787 unsigned int x= 0;
3788 memcached_server_st servers[num_hosts];
3789 memcpy(servers, memc->hosts, sizeof(memcached_server_st) * num_hosts);
3790 for (x= 0; x < num_hosts; x++)
3791 memcached_server_free(&memc->hosts[x]);
3792
3793 memc->number_of_hosts= 0;
3794 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_USE_UDP, 1);
3795 for (x= 0; x < num_hosts; x++)
3796 {
3797 assert(memcached_server_add_udp(memc, servers[x].hostname, servers[x].port) == MEMCACHED_SUCCESS);
3798 assert(memc->hosts[x].write_buffer_offset == UDP_DATAGRAM_HEADER_LENGTH);
3799 }
3800
3801 return MEMCACHED_SUCCESS;
3802 }
3803
3804 static memcached_return binary_init_udp(memcached_st *memc)
3805 {
3806 pre_binary(memc);
3807 return init_udp(memc);
3808 }
3809
3810 /* Make sure that I cant add a tcp server to a udp client */
3811 static test_return add_tcp_server_udp_client_test(memcached_st *memc)
3812 {
3813 memcached_server_st server;
3814 memcached_server_clone(&server, &memc->hosts[0]);
3815 assert(memcached_server_remove(&(memc->hosts[0])) == MEMCACHED_SUCCESS);
3816 assert(memcached_server_add(memc, server.hostname, server.port) == MEMCACHED_INVALID_HOST_PROTOCOL);
3817 return TEST_SUCCESS;
3818 }
3819
3820 /* Make sure that I cant add a udp server to a tcp client */
3821 static test_return add_udp_server_tcp_client_test(memcached_st *memc)
3822 {
3823 memcached_server_st server;
3824 memcached_server_clone(&server, &memc->hosts[0]);
3825 assert(memcached_server_remove(&(memc->hosts[0])) == MEMCACHED_SUCCESS);
3826
3827 memcached_st tcp_client;
3828 memcached_create(&tcp_client);
3829 assert(memcached_server_add_udp(&tcp_client, server.hostname, server.port) == MEMCACHED_INVALID_HOST_PROTOCOL);
3830 return TEST_SUCCESS;
3831 }
3832
3833 static test_return set_udp_behavior_test(memcached_st *memc)
3834 {
3835
3836 memcached_quit(memc);
3837 memc->number_of_hosts= 0;
3838 run_distribution(memc);
3839 assert(memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_USE_UDP, 1) == MEMCACHED_SUCCESS);
3840 assert(memc->flags & MEM_USE_UDP);
3841 assert(memc->flags & MEM_NOREPLY);;
3842
3843 assert(memc->number_of_hosts == 0);
3844
3845 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_USE_UDP,0);
3846 assert(!(memc->flags & MEM_USE_UDP));
3847 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_NOREPLY,0);
3848 assert(!(memc->flags & MEM_NOREPLY));
3849 return TEST_SUCCESS;
3850 }
3851
3852 static test_return udp_set_test(memcached_st *memc)
3853 {
3854 unsigned int x= 0;
3855 unsigned int num_iters= 1025; //request id rolls over at 1024
3856 for (x= 0; x < num_iters;x++)
3857 {
3858 memcached_return rc;
3859 char *key= "foo";
3860 char *value= "when we sanitize";
3861 uint16_t *expected_ids= get_udp_request_ids(memc);
3862 unsigned int server_key= memcached_generate_hash(memc,key,strlen(key));
3863 size_t init_offset= memc->hosts[server_key].write_buffer_offset;
3864 rc= memcached_set(memc, key, strlen(key),
3865 value, strlen(value),
3866 (time_t)0, (uint32_t)0);
3867 assert(rc == MEMCACHED_SUCCESS || rc == MEMCACHED_BUFFERED);
3868 /** NB, the check below assumes that if new write_ptr is less than
3869 * the original write_ptr that we have flushed. For large payloads, this
3870 * maybe an invalid assumption, but for the small payload we have it is OK
3871 */
3872 if (rc == MEMCACHED_SUCCESS ||
3873 memc->hosts[server_key].write_buffer_offset < init_offset)
3874 increment_request_id(&expected_ids[server_key]);
3875
3876 if (rc == MEMCACHED_SUCCESS)
3877 {
3878 assert(memc->hosts[server_key].write_buffer_offset == UDP_DATAGRAM_HEADER_LENGTH);
3879 }
3880 else
3881 {
3882 assert(memc->hosts[server_key].write_buffer_offset != UDP_DATAGRAM_HEADER_LENGTH);
3883 assert(memc->hosts[server_key].write_buffer_offset <= MAX_UDP_DATAGRAM_LENGTH);
3884 }
3885 assert(post_udp_op_check(memc,expected_ids) == TEST_SUCCESS);
3886 }
3887 return TEST_SUCCESS;
3888 }
3889
3890 static test_return udp_buffered_set_test(memcached_st *memc)
3891 {
3892 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_BUFFER_REQUESTS, 1);
3893 return udp_set_test(memc);
3894 }
3895
3896 static test_return udp_set_too_big_test(memcached_st *memc)
3897 {
3898 memcached_return rc;
3899 char *key= "bar";
3900 char value[MAX_UDP_DATAGRAM_LENGTH];
3901 uint16_t *expected_ids= get_udp_request_ids(memc);
3902 rc= memcached_set(memc, key, strlen(key),
3903 value, MAX_UDP_DATAGRAM_LENGTH,
3904 (time_t)0, (uint32_t)0);
3905 assert(rc == MEMCACHED_WRITE_FAILURE);
3906 return post_udp_op_check(memc,expected_ids);
3907 }
3908
3909 static test_return udp_delete_test(memcached_st *memc)
3910 {
3911 unsigned int x= 0;
3912 unsigned int num_iters= 1025; //request id rolls over at 1024
3913 for (x= 0; x < num_iters;x++)
3914 {
3915 memcached_return rc;
3916 char *key= "foo";
3917 uint16_t *expected_ids=get_udp_request_ids(memc);
3918 unsigned int server_key= memcached_generate_hash(memc, key, strlen(key));
3919 size_t init_offset= memc->hosts[server_key].write_buffer_offset;
3920 rc= memcached_delete(memc, key, strlen(key), 0);
3921 assert(rc == MEMCACHED_SUCCESS || rc == MEMCACHED_BUFFERED);
3922 if (rc == MEMCACHED_SUCCESS || memc->hosts[server_key].write_buffer_offset < init_offset)
3923 increment_request_id(&expected_ids[server_key]);
3924 if (rc == MEMCACHED_SUCCESS)
3925 assert(memc->hosts[server_key].write_buffer_offset == UDP_DATAGRAM_HEADER_LENGTH);
3926 else
3927 {
3928 assert(memc->hosts[server_key].write_buffer_offset != UDP_DATAGRAM_HEADER_LENGTH);
3929 assert(memc->hosts[server_key].write_buffer_offset <= MAX_UDP_DATAGRAM_LENGTH);
3930 }
3931 assert(post_udp_op_check(memc,expected_ids) == TEST_SUCCESS);
3932 }
3933 return TEST_SUCCESS;
3934 }
3935
3936 static test_return udp_buffered_delete_test(memcached_st *memc)
3937 {
3938 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_BUFFER_REQUESTS, 1);
3939 return udp_delete_test(memc);
3940 }
3941
3942 static test_return udp_verbosity_test(memcached_st *memc)
3943 {
3944 memcached_return rc;
3945 uint16_t *expected_ids= get_udp_request_ids(memc);
3946 unsigned int x;
3947 for (x= 0; x < memc->number_of_hosts;x++)
3948 increment_request_id(&expected_ids[x]);
3949
3950 rc= memcached_verbosity(memc,3);
3951 assert(rc == MEMCACHED_SUCCESS);
3952 return post_udp_op_check(memc,expected_ids);
3953 }
3954
3955 static test_return udp_quit_test(memcached_st *memc)
3956 {
3957 uint16_t *expected_ids= get_udp_request_ids(memc);
3958 memcached_quit(memc);
3959 return post_udp_op_check(memc, expected_ids);
3960 }
3961
3962 static test_return udp_flush_test(memcached_st *memc)
3963 {
3964 memcached_return rc;
3965 uint16_t *expected_ids= get_udp_request_ids(memc);
3966 unsigned int x;
3967 for (x= 0; x < memc->number_of_hosts;x++)
3968 increment_request_id(&expected_ids[x]);
3969
3970 rc= memcached_flush(memc,0);
3971 assert(rc == MEMCACHED_SUCCESS);
3972 return post_udp_op_check(memc,expected_ids);
3973 }
3974
3975 static test_return udp_incr_test(memcached_st *memc)
3976 {
3977 memcached_return rc;
3978 char *key= "incr";
3979 char *value= "1";
3980 rc= memcached_set(memc, key, strlen(key),
3981 value, strlen(value),
3982 (time_t)0, (uint32_t)0);
3983
3984 assert(rc == MEMCACHED_SUCCESS);
3985 uint16_t *expected_ids= get_udp_request_ids(memc);
3986 unsigned int server_key= memcached_generate_hash(memc, key, strlen(key));
3987 increment_request_id(&expected_ids[server_key]);
3988 uint64_t newvalue;
3989 rc= memcached_increment(memc, key, strlen(key), 1, &newvalue);
3990 assert(rc == MEMCACHED_SUCCESS);
3991 return post_udp_op_check(memc, expected_ids);
3992 }
3993
3994 static test_return udp_decr_test(memcached_st *memc)
3995 {
3996 memcached_return rc;
3997 char *key= "decr";
3998 char *value= "1";
3999 rc= memcached_set(memc, key, strlen(key),
4000 value, strlen(value),
4001 (time_t)0, (uint32_t)0);
4002
4003 assert(rc == MEMCACHED_SUCCESS);
4004 uint16_t *expected_ids= get_udp_request_ids(memc);
4005 unsigned int server_key= memcached_generate_hash(memc, key, strlen(key));
4006 increment_request_id(&expected_ids[server_key]);
4007 uint64_t newvalue;
4008 rc= memcached_decrement(memc, key, strlen(key), 1, &newvalue);
4009 assert(rc == MEMCACHED_SUCCESS);
4010 return post_udp_op_check(memc, expected_ids);
4011 }
4012
4013
4014 static test_return udp_stat_test(memcached_st *memc)
4015 {
4016 memcached_stat_st * rv= NULL;
4017 memcached_return rc;
4018 char args[]= "";
4019 uint16_t *expected_ids = get_udp_request_ids(memc);
4020 rv = memcached_stat(memc, args, &rc);
4021 free(rv);
4022 assert(rc == MEMCACHED_NOT_SUPPORTED);
4023 return post_udp_op_check(memc, expected_ids);
4024 }
4025
4026 static test_return udp_version_test(memcached_st *memc)
4027 {
4028 memcached_return rc;
4029 uint16_t *expected_ids = get_udp_request_ids(memc);
4030 rc = memcached_version(memc);
4031 assert(rc == MEMCACHED_NOT_SUPPORTED);
4032 return post_udp_op_check(memc, expected_ids);
4033 }
4034
4035 static test_return udp_get_test(memcached_st *memc)
4036 {
4037 memcached_return rc;
4038 char *key= "foo";
4039 size_t vlen;
4040 uint16_t *expected_ids = get_udp_request_ids(memc);
4041 char *val= memcached_get(memc, key, strlen(key), &vlen, (uint32_t)0, &rc);
4042 assert(rc == MEMCACHED_NOT_SUPPORTED);
4043 assert(val == NULL);
4044 return post_udp_op_check(memc, expected_ids);
4045 }
4046
4047 static test_return udp_mixed_io_test(memcached_st *memc)
4048 {
4049 test_st current_op;
4050 test_st mixed_io_ops [] ={
4051 {"udp_set_test", 0, udp_set_test},
4052 {"udp_set_too_big_test", 0, udp_set_too_big_test},
4053 {"udp_delete_test", 0, udp_delete_test},
4054 {"udp_verbosity_test", 0, udp_verbosity_test},
4055 {"udp_quit_test", 0, udp_quit_test},
4056 {"udp_flush_test", 0, udp_flush_test},
4057 {"udp_incr_test", 0, udp_incr_test},
4058 {"udp_decr_test", 0, udp_decr_test},
4059 {"udp_version_test", 0, udp_version_test}
4060 };
4061 unsigned int x= 0;
4062 for (x= 0; x < 500; x++)
4063 {
4064 current_op= mixed_io_ops[random() % 9];
4065 assert(current_op.function(memc) == TEST_SUCCESS);
4066 }
4067 return TEST_SUCCESS;
4068 }
4069
4070 static test_return hsieh_avaibility_test (memcached_st *memc)
4071 {
4072 memcached_return expected_rc= MEMCACHED_FAILURE;
4073 #ifdef HAVE_HSIEH_HASH
4074 expected_rc= MEMCACHED_SUCCESS;
4075 #endif
4076 memcached_return rc= memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_HASH,
4077 (uint64_t)MEMCACHED_HASH_HSIEH);
4078 assert(rc == expected_rc);
4079 return TEST_SUCCESS;
4080 }
4081
4082 static char *list[]=
4083 {
4084 "apple",
4085 "beat",
4086 "carrot",
4087 "daikon",
4088 "eggplant",
4089 "flower",
4090 "green",
4091 "hide",
4092 "ick",
4093 "jack",
4094 "kick",
4095 "lime",
4096 "mushrooms",
4097 "nectarine",
4098 "orange",
4099 "peach",
4100 "quant",
4101 "ripen",
4102 "strawberry",
4103 "tang",
4104 "up",
4105 "volumne",
4106 "when",
4107 "yellow",
4108 "zip",
4109 NULL
4110 };
4111
4112 static test_return md5_run (memcached_st *memc __attribute__((unused)))
4113 {
4114 uint32_t x;
4115 char **ptr;
4116 uint32_t values[]= { 3195025439, 2556848621, 3724893440, 3332385401, 245758794, 2550894432,
4117 121710495, 3053817768, 1250994555, 1862072655, 2631955953, 2951528551,
4118 1451250070, 2820856945, 2060845566, 3646985608, 2138080750, 217675895,
4119 2230934345, 1234361223, 3968582726, 2455685270, 1293568479, 199067604,
4120 2042482093 };
4121
4122
4123 for (ptr= list, x= 0; *ptr; ptr++, x++)
4124 {
4125 uint32_t hash_val;
4126
4127 hash_val= memcached_generate_hash_value(*ptr, strlen(*ptr), MEMCACHED_HASH_MD5);
4128 assert(values[x] == hash_val);
4129 }
4130
4131 return TEST_SUCCESS;
4132 }
4133
4134 static test_return crc_run (memcached_st *memc __attribute__((unused)))
4135 {
4136 uint32_t x;
4137 char **ptr;
4138 uint32_t values[]= { 10542, 22009, 14526, 19510, 19432, 10199, 20634, 9369, 11511, 10362,
4139 7893, 31289, 11313, 9354, 7621, 30628, 15218, 25967, 2695, 9380,
4140 17300, 28156, 9192, 20484, 16925 };
4141
4142 for (ptr= list, x= 0; *ptr; ptr++, x++)
4143 {
4144 uint32_t hash_val;
4145
4146 hash_val= memcached_generate_hash_value(*ptr, strlen(*ptr), MEMCACHED_HASH_CRC);
4147 assert(values[x] == hash_val);
4148 }
4149
4150 return TEST_SUCCESS;
4151 }
4152
4153 static test_return fnv1_64_run (memcached_st *memc __attribute__((unused)))
4154 {
4155 uint32_t x;
4156 char **ptr;
4157 uint32_t values[]= { 473199127, 4148981457, 3971873300, 3257986707, 1722477987, 2991193800,
4158 4147007314, 3633179701, 1805162104, 3503289120, 3395702895, 3325073042,
4159 2345265314, 3340346032, 2722964135, 1173398992, 2815549194, 2562818319,
4160 224996066, 2680194749, 3035305390, 246890365, 2395624193, 4145193337,
4161 1801941682 };
4162
4163 for (ptr= list, x= 0; *ptr; ptr++, x++)
4164 {
4165 uint32_t hash_val;
4166
4167 hash_val= memcached_generate_hash_value(*ptr, strlen(*ptr), MEMCACHED_HASH_FNV1_64);
4168 assert(values[x] == hash_val);
4169 }
4170
4171 return TEST_SUCCESS;
4172 }
4173
4174 static test_return fnv1a_64_run (memcached_st *memc __attribute__((unused)))
4175 {
4176 uint32_t x;
4177 char **ptr;
4178 uint32_t values[]= { 1488911807, 2500855813, 1510099634, 1390325195, 3647689787, 3241528582,
4179 1669328060, 2604311949, 734810122, 1516407546, 560948863, 1767346780,
4180 561034892, 4156330026, 3716417003, 3475297030, 1518272172, 227211583,
4181 3938128828, 126112909, 3043416448, 3131561933, 1328739897, 2455664041,
4182 2272238452 };
4183
4184 for (ptr= list, x= 0; *ptr; ptr++, x++)
4185 {
4186 uint32_t hash_val;
4187
4188 hash_val= memcached_generate_hash_value(*ptr, strlen(*ptr), MEMCACHED_HASH_FNV1A_64);
4189 assert(values[x] == hash_val);
4190 }
4191
4192 return TEST_SUCCESS;
4193 }
4194
4195 static test_return fnv1_32_run (memcached_st *memc __attribute__((unused)))
4196 {
4197 uint32_t x;
4198 char **ptr;
4199 uint32_t values[]= { 67176023, 1190179409, 2043204404, 3221866419, 2567703427, 3787535528, 4147287986,
4200 3500475733, 344481048, 3865235296, 2181839183, 119581266, 510234242, 4248244304,
4201 1362796839, 103389328, 1449620010, 182962511, 3554262370, 3206747549, 1551306158,
4202 4127558461, 1889140833, 2774173721, 1180552018 };
4203
4204
4205 for (ptr= list, x= 0; *ptr; ptr++, x++)
4206 {
4207 uint32_t hash_val;
4208
4209 hash_val= memcached_generate_hash_value(*ptr, strlen(*ptr), MEMCACHED_HASH_FNV1_32);
4210 assert(values[x] == hash_val);
4211 }
4212
4213 return TEST_SUCCESS;
4214 }
4215
4216 static test_return fnv1a_32_run (memcached_st *memc __attribute__((unused)))
4217 {
4218 uint32_t x;
4219 char **ptr;
4220 uint32_t values[]= { 280767167, 2421315013, 3072375666, 855001899, 459261019, 3521085446, 18738364,
4221 1625305005, 2162232970, 777243802, 3323728671, 132336572, 3654473228, 260679466,
4222 1169454059, 2698319462, 1062177260, 235516991, 2218399068, 405302637, 1128467232,
4223 3579622413, 2138539289, 96429129, 2877453236 };
4224
4225 for (ptr= list, x= 0; *ptr; ptr++, x++)
4226 {
4227 uint32_t hash_val;
4228
4229 hash_val= memcached_generate_hash_value(*ptr, strlen(*ptr), MEMCACHED_HASH_FNV1A_32);
4230 assert(values[x] == hash_val);
4231 }
4232
4233 return TEST_SUCCESS;
4234 }
4235
4236 static test_return hsieh_run (memcached_st *memc __attribute__((unused)))
4237 {
4238 uint32_t x;
4239 char **ptr;
4240 #ifdef HAVE_HSIEH_HASH
4241 uint32_t values[]= { 3738850110, 3636226060, 3821074029, 3489929160, 3485772682, 80540287,
4242 1805464076, 1895033657, 409795758, 979934958, 3634096985, 1284445480,
4243 2265380744, 707972988, 353823508, 1549198350, 1327930172, 9304163,
4244 4220749037, 2493964934, 2777873870, 2057831732, 1510213931, 2027828987,
4245 3395453351 };
4246 #else
4247 uint32_t values[]= { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1 };
4248 #endif
4249
4250 for (ptr= list, x= 0; *ptr; ptr++, x++)
4251 {
4252 uint32_t hash_val;
4253
4254 hash_val= memcached_generate_hash_value(*ptr, strlen(*ptr), MEMCACHED_HASH_HSIEH);
4255 assert(values[x] == hash_val);
4256 }
4257
4258 return TEST_SUCCESS;
4259 }
4260
4261 static test_return murmur_run (memcached_st *memc __attribute__((unused)))
4262 {
4263 uint32_t x;
4264 char **ptr;
4265 uint32_t values[]= { 473199127, 4148981457, 3971873300, 3257986707, 1722477987, 2991193800,
4266 4147007314, 3633179701, 1805162104, 3503289120, 3395702895, 3325073042,
4267 2345265314, 3340346032, 2722964135, 1173398992, 2815549194, 2562818319,
4268 224996066, 2680194749, 3035305390, 246890365, 2395624193, 4145193337,
4269 1801941682 };
4270
4271 for (ptr= list, x= 0; *ptr; ptr++, x++)
4272 {
4273 uint32_t hash_val;
4274
4275 hash_val= memcached_generate_hash_value(*ptr, strlen(*ptr), MEMCACHED_HASH_FNV1_64);
4276 assert(values[x] == hash_val);
4277 }
4278
4279 return TEST_SUCCESS;
4280 }
4281
4282 static test_return jenkins_run (memcached_st *memc __attribute__((unused)))
4283 {
4284 uint32_t x;
4285 char **ptr;
4286 uint32_t values[]= { 1442444624, 4253821186, 1885058256, 2120131735, 3261968576, 3515188778,
4287 4232909173, 4288625128, 1812047395, 3689182164, 2502979932, 1214050606,
4288 2415988847, 1494268927, 1025545760, 3920481083, 4153263658, 3824871822,
4289 3072759809, 798622255, 3065432577, 1453328165, 2691550971, 3408888387,
4290 2629893356 };
4291
4292
4293 for (ptr= list, x= 0; *ptr; ptr++, x++)
4294 {
4295 uint32_t hash_val;
4296
4297 hash_val= memcached_generate_hash_value(*ptr, strlen(*ptr), MEMCACHED_HASH_JENKINS);
4298 assert(values[x] == hash_val);
4299 }
4300
4301 return TEST_SUCCESS;
4302 }
4303
4304 test_st udp_setup_server_tests[] ={
4305 {"set_udp_behavior_test", 0, set_udp_behavior_test},
4306 {"add_tcp_server_udp_client_test", 0, add_tcp_server_udp_client_test},
4307 {"add_udp_server_tcp_client_test", 0, add_udp_server_tcp_client_test},
4308 {0, 0, 0}
4309 };
4310
4311 test_st upd_io_tests[] ={
4312 {"udp_set_test", 0, udp_set_test},
4313 {"udp_buffered_set_test", 0, udp_buffered_set_test},
4314 {"udp_set_too_big_test", 0, udp_set_too_big_test},
4315 {"udp_delete_test", 0, udp_delete_test},
4316 {"udp_buffered_delete_test", 0, udp_buffered_delete_test},
4317 {"udp_verbosity_test", 0, udp_verbosity_test},
4318 {"udp_quit_test", 0, udp_quit_test},
4319 {"udp_flush_test", 0, udp_flush_test},
4320 {"udp_incr_test", 0, udp_incr_test},
4321 {"udp_decr_test", 0, udp_decr_test},
4322 {"udp_stat_test", 0, udp_stat_test},
4323 {"udp_version_test", 0, udp_version_test},
4324 {"udp_get_test", 0, udp_get_test},
4325 {"udp_mixed_io_test", 0, udp_mixed_io_test},
4326 {0, 0, 0}
4327 };
4328
4329 /* Clean the server before beginning testing */
4330 test_st tests[] ={
4331 {"flush", 0, flush_test },
4332 {"init", 0, init_test },
4333 {"allocation", 0, allocation_test },
4334 {"server_list_null_test", 0, server_list_null_test},
4335 {"server_unsort", 0, server_unsort_test},
4336 {"server_sort", 0, server_sort_test},
4337 {"server_sort2", 0, server_sort2_test},
4338 {"clone_test", 0, clone_test },
4339 {"connection_test", 0, connection_test},
4340 {"callback_test", 0, callback_test},
4341 {"behavior_test", 0, behavior_test},
4342 {"userdata_test", 0, userdata_test},
4343 {"error", 0, error_test },
4344 {"set", 0, set_test },
4345 {"set2", 0, set_test2 },
4346 {"set3", 0, set_test3 },
4347 {"dump", 1, dump_test},
4348 {"add", 1, add_test },
4349 {"replace", 1, replace_test },
4350 {"delete", 1, delete_test },
4351 {"get", 1, get_test },
4352 {"get2", 0, get_test2 },
4353 {"get3", 0, get_test3 },
4354 {"get4", 0, get_test4 },
4355 {"partial mget", 0, get_test5 },
4356 {"stats_servername", 0, stats_servername_test },
4357 {"increment", 0, increment_test },
4358 {"increment_with_initial", 1, increment_with_initial_test },
4359 {"decrement", 0, decrement_test },
4360 {"decrement_with_initial", 1, decrement_with_initial_test },
4361 {"quit", 0, quit_test },
4362 {"mget", 1, mget_test },
4363 {"mget_result", 1, mget_result_test },
4364 {"mget_result_alloc", 1, mget_result_alloc_test },
4365 {"mget_result_function", 1, mget_result_function },
4366 {"get_stats", 0, get_stats },
4367 {"add_host_test", 0, add_host_test },
4368 {"add_host_test_1", 0, add_host_test1 },
4369 {"get_stats_keys", 0, get_stats_keys },
4370 {"behavior_test", 0, get_stats_keys },
4371 {"callback_test", 0, get_stats_keys },
4372 {"version_string_test", 0, version_string_test},
4373 {"bad_key", 1, bad_key_test },
4374 {"memcached_server_cursor", 1, memcached_server_cursor_test },
4375 {"read_through", 1, read_through },
4376 {"delete_through", 1, delete_through },
4377 {"noreply", 1, noreply_test},
4378 {"analyzer", 1, analyzer_test},
4379 #ifdef HAVE_LIBMEMCACHEDUTIL
4380 {"connectionpool", 1, connection_pool_test },
4381 #endif
4382 {0, 0, 0}
4383 };
4384
4385 test_st async_tests[] ={
4386 {"add", 1, add_wrapper },
4387 {0, 0, 0}
4388 };
4389
4390 test_st string_tests[] ={
4391 {"string static with null", 0, string_static_null },
4392 {"string alloc with null", 0, string_alloc_null },
4393 {"string alloc with 1K", 0, string_alloc_with_size },
4394 {"string alloc with malloc failure", 0, string_alloc_with_size_toobig },
4395 {"string append", 0, string_alloc_append },
4396 {"string append failure (too big)", 0, string_alloc_append_toobig },
4397 {0, 0, 0}
4398 };
4399
4400 test_st result_tests[] ={
4401 {"result static", 0, result_static},
4402 {"result alloc", 0, result_alloc},
4403 {0, 0, 0}
4404 };
4405
4406 test_st version_1_2_3[] ={
4407 {"append", 0, append_test },
4408 {"prepend", 0, prepend_test },
4409 {"cas", 0, cas_test },
4410 {"cas2", 0, cas2_test },
4411 {"append_binary", 0, append_binary_test },
4412 {0, 0, 0}
4413 };
4414
4415 test_st user_tests[] ={
4416 {"user_supplied_bug1", 0, user_supplied_bug1 },
4417 {"user_supplied_bug2", 0, user_supplied_bug2 },
4418 {"user_supplied_bug3", 0, user_supplied_bug3 },
4419 {"user_supplied_bug4", 0, user_supplied_bug4 },
4420 {"user_supplied_bug5", 1, user_supplied_bug5 },
4421 {"user_supplied_bug6", 1, user_supplied_bug6 },
4422 {"user_supplied_bug7", 1, user_supplied_bug7 },
4423 {"user_supplied_bug8", 1, user_supplied_bug8 },
4424 {"user_supplied_bug9", 1, user_supplied_bug9 },
4425 {"user_supplied_bug10", 1, user_supplied_bug10 },
4426 {"user_supplied_bug11", 1, user_supplied_bug11 },
4427 {"user_supplied_bug12", 1, user_supplied_bug12 },
4428 {"user_supplied_bug13", 1, user_supplied_bug13 },
4429 {"user_supplied_bug14", 1, user_supplied_bug14 },
4430 {"user_supplied_bug15", 1, user_supplied_bug15 },
4431 {"user_supplied_bug16", 1, user_supplied_bug16 },
4432 #ifndef __sun
4433 /*
4434 ** It seems to be something weird with the character sets..
4435 ** value_fetch is unable to parse the value line (iscntrl "fails"), so I
4436 ** guess I need to find out how this is supposed to work.. Perhaps I need
4437 ** to run the test in a specific locale (I tried zh_CN.UTF-8 without success,
4438 ** so just disable the code for now...).
4439 */
4440 {"user_supplied_bug17", 1, user_supplied_bug17 },
4441 #endif
4442 {"user_supplied_bug18", 1, user_supplied_bug18 },
4443 {"user_supplied_bug19", 1, user_supplied_bug19 },
4444 {"user_supplied_bug20", 1, user_supplied_bug20 },
4445 {0, 0, 0}
4446 };
4447
4448 test_st replication_tests[]= {
4449 {"set", 1, replication_set_test },
4450 {"get", 0, replication_get_test },
4451 {"mget", 0, replication_mget_test },
4452 {"delete", 0, replication_delete_test },
4453 {0, 0, 0}
4454 };
4455
4456 test_st generate_tests[] ={
4457 {"generate_pairs", 1, generate_pairs },
4458 {"generate_data", 1, generate_data },
4459 {"get_read", 0, get_read },
4460 {"delete_generate", 0, delete_generate },
4461 {"generate_buffer_data", 1, generate_buffer_data },
4462 {"delete_buffer", 0, delete_buffer_generate},
4463 {"generate_data", 1, generate_data },
4464 {"mget_read", 0, mget_read },
4465 {"mget_read_result", 0, mget_read_result },
4466 {"mget_read_function", 0, mget_read_function },
4467 {"cleanup", 1, cleanup_pairs },
4468 {"generate_large_pairs", 1, generate_large_pairs },
4469 {"generate_data", 1, generate_data },
4470 {"generate_buffer_data", 1, generate_buffer_data },
4471 {"cleanup", 1, cleanup_pairs },
4472 {0, 0, 0}
4473 };
4474
4475 test_st consistent_tests[] ={
4476 {"generate_pairs", 1, generate_pairs },
4477 {"generate_data", 1, generate_data },
4478 {"get_read", 0, get_read_count },
4479 {"cleanup", 1, cleanup_pairs },
4480 {0, 0, 0}
4481 };
4482
4483 test_st consistent_weighted_tests[] ={
4484 {"generate_pairs", 1, generate_pairs },
4485 {"generate_data", 1, generate_data_with_stats },
4486 {"get_read", 0, get_read_count },
4487 {"cleanup", 1, cleanup_pairs },
4488 {0, 0, 0}
4489 };
4490
4491 test_st hsieh_availability[] ={
4492 {"hsieh_avaibility_test",0,hsieh_avaibility_test},
4493 {0, 0, 0}
4494 };
4495
4496 test_st ketama_auto_eject_hosts[] ={
4497 {"auto_eject_hosts", 1, auto_eject_hosts },
4498 {0, 0, 0}
4499 };
4500
4501 test_st hash_tests[] ={
4502 {"md5", 0, md5_run },
4503 {"crc", 0, crc_run },
4504 {"fnv1_64", 0, fnv1_64_run },
4505 {"fnv1a_64", 0, fnv1a_64_run },
4506 {"fnv1_32", 0, fnv1_32_run },
4507 {"fnv1a_32", 0, fnv1a_32_run },
4508 {"hsieh", 0, hsieh_run },
4509 {"murmur", 0, murmur_run },
4510 {"jenkis", 0, jenkins_run },
4511 {0, 0, 0}
4512 };
4513
4514 collection_st collection[] ={
4515 {"hsieh_availability",0,0,hsieh_availability},
4516 {"udp_setup", init_udp, 0, udp_setup_server_tests},
4517 {"udp_io", init_udp, 0, upd_io_tests},
4518 {"udp_binary_io", binary_init_udp, 0, upd_io_tests},
4519 {"block", 0, 0, tests},
4520 {"binary", pre_binary, 0, tests},
4521 {"nonblock", pre_nonblock, 0, tests},
4522 {"nodelay", pre_nodelay, 0, tests},
4523 {"settimer", pre_settimer, 0, tests},
4524 {"md5", pre_md5, 0, tests},
4525 {"crc", pre_crc, 0, tests},
4526 {"hsieh", pre_hsieh, 0, tests},
4527 {"jenkins", pre_jenkins, 0, tests},
4528 {"fnv1_64", pre_hash_fnv1_64, 0, tests},
4529 {"fnv1a_64", pre_hash_fnv1a_64, 0, tests},
4530 {"fnv1_32", pre_hash_fnv1_32, 0, tests},
4531 {"fnv1a_32", pre_hash_fnv1a_32, 0, tests},
4532 {"ketama", pre_behavior_ketama, 0, tests},
4533 {"ketama_auto_eject_hosts", pre_behavior_ketama, 0, ketama_auto_eject_hosts},
4534 {"unix_socket", pre_unix_socket, 0, tests},
4535 {"unix_socket_nodelay", pre_nodelay, 0, tests},
4536 {"poll_timeout", poll_timeout, 0, tests},
4537 {"gets", enable_cas, 0, tests},
4538 {"consistent", enable_consistent, 0, tests},
4539 {"deprecated_memory_allocators", deprecated_set_memory_alloc, 0, tests},
4540 {"memory_allocators", set_memory_alloc, 0, tests},
4541 {"prefix", set_prefix, 0, tests},
4542 {"version_1_2_3", check_for_1_2_3, 0, version_1_2_3},
4543 {"string", 0, 0, string_tests},
4544 {"result", 0, 0, result_tests},
4545 {"async", pre_nonblock, 0, async_tests},
4546 {"async_binary", pre_nonblock_binary, 0, async_tests},
4547 {"user", 0, 0, user_tests},
4548 {"generate", 0, 0, generate_tests},
4549 {"generate_hsieh", pre_hsieh, 0, generate_tests},
4550 {"generate_ketama", pre_behavior_ketama, 0, generate_tests},
4551 {"generate_hsieh_consistent", enable_consistent, 0, generate_tests},
4552 {"generate_md5", pre_md5, 0, generate_tests},
4553 {"generate_murmur", pre_murmur, 0, generate_tests},
4554 {"generate_jenkins", pre_jenkins, 0, generate_tests},
4555 {"generate_nonblock", pre_nonblock, 0, generate_tests},
4556 {"consistent_not", 0, 0, consistent_tests},
4557 {"consistent_ketama", pre_behavior_ketama, 0, consistent_tests},
4558 {"consistent_ketama_weighted", pre_behavior_ketama_weighted, 0, consistent_weighted_tests},
4559 {"test_hashes", 0, 0, hash_tests},
4560 {"replication", pre_replication, 0, replication_tests},
4561 {0, 0, 0, 0}
4562 };
4563
4564 #define SERVERS_TO_CREATE 5
4565
4566 /* Prototypes for functions we will pass to test framework */
4567 void *world_create(void);
4568 void world_destroy(void *p);
4569
4570 void *world_create(void)
4571 {
4572 server_startup_st *construct;
4573
4574 construct= (server_startup_st *)malloc(sizeof(server_startup_st));
4575 memset(construct, 0, sizeof(server_startup_st));
4576 construct->count= SERVERS_TO_CREATE;
4577 construct->udp= 0;
4578 server_startup(construct);
4579
4580 return construct;
4581 }
4582
4583
4584 void world_destroy(void *p)
4585 {
4586 server_startup_st *construct= (server_startup_st *)p;
4587 memcached_server_st *servers= (memcached_server_st *)construct->servers;
4588 memcached_server_list_free(servers);
4589
4590 server_shutdown(construct);
4591 free(construct);
4592 }
4593
4594 void get_world(world_st *world)
4595 {
4596 world->collections= collection;
4597 world->create= world_create;
4598 world->destroy= world_destroy;
4599 }