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