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