40415dafb75588ddc9af970fafa3df8d8da4d642
[awesomized/libmemcached] / tests / function.c
1 /*
2 Sample test application.
3 */
4 #include <assert.h>
5 #include <stdio.h>
6 #include <stdlib.h>
7 #include <string.h>
8 #include <sys/time.h>
9 #include <sys/types.h>
10 #include <sys/stat.h>
11 #include <unistd.h>
12 #include <time.h>
13 #include "server.h"
14 #include "../clients/generator.h"
15 #include "../clients/execute.h"
16
17 #ifndef INT64_MAX
18 #define INT64_MAX LONG_MAX
19 #endif
20 #ifndef INT32_MAX
21 #define INT32_MAX INT_MAX
22 #endif
23
24
25 #include "test.h"
26
27 #define GLOBAL_COUNT 10000
28 #define GLOBAL2_COUNT 100
29 #define SERVERS_TO_CREATE 5
30 static uint32_t global_count;
31
32 static pairs_st *global_pairs;
33 static char *global_keys[GLOBAL_COUNT];
34 static size_t global_keys_length[GLOBAL_COUNT];
35
36 static test_return init_test(memcached_st *not_used __attribute__((unused)))
37 {
38 memcached_st memc;
39
40 (void)memcached_create(&memc);
41 memcached_free(&memc);
42
43 return 0;
44 }
45
46 static test_return server_list_null_test(memcached_st *ptr __attribute__((unused)))
47 {
48 memcached_server_st *server_list;
49 memcached_return rc;
50
51 server_list= memcached_server_list_append_with_weight(NULL, NULL, 0, 0, NULL);
52 assert(server_list == NULL);
53
54 server_list= memcached_server_list_append_with_weight(NULL, "localhost", 0, 0, NULL);
55 assert(server_list == NULL);
56
57 server_list= memcached_server_list_append_with_weight(NULL, NULL, 0, 0, &rc);
58 assert(server_list == NULL);
59
60 return 0;
61 }
62
63 #define TEST_PORT_COUNT 7
64 uint32_t test_ports[TEST_PORT_COUNT];
65
66 static memcached_return server_display_function(memcached_st *ptr __attribute__((unused)), memcached_server_st *server, void *context)
67 {
68 /* Do Nothing */
69 uint32_t bigger= *((uint32_t *)(context));
70 assert(bigger <= server->port);
71 *((uint32_t *)(context))= server->port;
72
73 return MEMCACHED_SUCCESS;
74 }
75
76 static test_return server_sort_test(memcached_st *ptr __attribute__((unused)))
77 {
78 uint32_t x;
79 uint32_t bigger= 0; /* Prime the value for the assert in server_display_function */
80 memcached_return rc;
81 memcached_server_function callbacks[1];
82 memcached_st *local_memc;
83
84 local_memc= memcached_create(NULL);
85 assert(local_memc);
86 memcached_behavior_set(local_memc, MEMCACHED_BEHAVIOR_SORT_HOSTS, 1);
87
88 for (x= 0; x < TEST_PORT_COUNT; x++)
89 {
90 test_ports[x]= random() % 64000;
91 rc= memcached_server_add_with_weight(local_memc, "localhost", test_ports[x], 0);
92 assert(local_memc->number_of_hosts == x + 1);
93 assert(local_memc->hosts[0].count == x+1);
94 assert(rc == MEMCACHED_SUCCESS);
95 }
96
97 callbacks[0]= server_display_function;
98 memcached_server_cursor(local_memc, callbacks, (void *)&bigger, 1);
99
100
101 memcached_free(local_memc);
102
103 return 0;
104 }
105
106 static test_return server_sort2_test(memcached_st *ptr __attribute__((unused)))
107 {
108 uint32_t bigger= 0; /* Prime the value for the assert in server_display_function */
109 memcached_return rc;
110 memcached_server_function callbacks[1];
111 memcached_st *local_memc;
112
113 local_memc= memcached_create(NULL);
114 assert(local_memc);
115 rc= memcached_behavior_set(local_memc, MEMCACHED_BEHAVIOR_SORT_HOSTS, 1);
116 assert(rc == MEMCACHED_SUCCESS);
117
118 rc= memcached_server_add_with_weight(local_memc, "MEMCACHED_BEHAVIOR_SORT_HOSTS", 43043, 0);
119 assert(rc == MEMCACHED_SUCCESS);
120 assert(local_memc->hosts[0].port == 43043);
121
122 rc= memcached_server_add_with_weight(local_memc, "MEMCACHED_BEHAVIOR_SORT_HOSTS", 43042, 0);
123 assert(rc == MEMCACHED_SUCCESS);
124 assert(local_memc->hosts[0].port == 43042);
125 assert(local_memc->hosts[1].port == 43043);
126
127 callbacks[0]= server_display_function;
128 memcached_server_cursor(local_memc, callbacks, (void *)&bigger, 1);
129
130
131 memcached_free(local_memc);
132
133 return 0;
134 }
135
136 static memcached_return server_display_unsort_function(memcached_st *ptr __attribute__((unused)), memcached_server_st *server, void *context)
137 {
138 /* Do Nothing */
139 uint32_t x= *((uint32_t *)(context));
140
141 assert(test_ports[x] == server->port);
142 *((uint32_t *)(context))= ++x;
143
144 return MEMCACHED_SUCCESS;
145 }
146
147 static test_return server_unsort_test(memcached_st *ptr __attribute__((unused)))
148 {
149 uint32_t x;
150 uint32_t counter= 0; /* Prime the value for the assert in server_display_function */
151 uint32_t bigger= 0; /* Prime the value for the assert in server_display_function */
152 memcached_return rc;
153 memcached_server_function callbacks[1];
154 memcached_st *local_memc;
155
156 local_memc= memcached_create(NULL);
157 assert(local_memc);
158
159 for (x= 0; x < TEST_PORT_COUNT; x++)
160 {
161 test_ports[x]= random() % 64000;
162 rc= memcached_server_add_with_weight(local_memc, "localhost", test_ports[x], 0);
163 assert(local_memc->number_of_hosts == x+1);
164 assert(local_memc->hosts[0].count == x+1);
165 assert(rc == MEMCACHED_SUCCESS);
166 }
167
168 callbacks[0]= server_display_unsort_function;
169 memcached_server_cursor(local_memc, callbacks, (void *)&counter, 1);
170
171 /* Now we sort old data! */
172 memcached_behavior_set(local_memc, MEMCACHED_BEHAVIOR_SORT_HOSTS, 1);
173 callbacks[0]= server_display_function;
174 memcached_server_cursor(local_memc, callbacks, (void *)&bigger, 1);
175
176
177 memcached_free(local_memc);
178
179 return 0;
180 }
181
182 static test_return allocation_test(memcached_st *not_used __attribute__((unused)))
183 {
184 memcached_st *memc;
185 memc= memcached_create(NULL);
186 assert(memc);
187 memcached_free(memc);
188
189 return 0;
190 }
191
192 static test_return clone_test(memcached_st *memc)
193 {
194 /* All null? */
195 {
196 memcached_st *clone;
197 clone= memcached_clone(NULL, NULL);
198 assert(clone);
199 memcached_free(clone);
200 }
201
202 /* Can we init from null? */
203 {
204 memcached_st *clone;
205 clone= memcached_clone(NULL, memc);
206 assert(clone);
207
208 assert(clone->call_free == memc->call_free);
209 assert(clone->call_malloc == memc->call_malloc);
210 assert(clone->call_realloc == memc->call_realloc);
211 assert(clone->connect_timeout == memc->connect_timeout);
212 assert(clone->delete_trigger == memc->delete_trigger);
213 assert(clone->distribution == memc->distribution);
214 assert(clone->flags == memc->flags);
215 assert(clone->get_key_failure == memc->get_key_failure);
216 assert(clone->hash == memc->hash);
217 assert(clone->hash_continuum == memc->hash_continuum);
218 assert(clone->io_bytes_watermark == memc->io_bytes_watermark);
219 assert(clone->io_msg_watermark == memc->io_msg_watermark);
220 assert(clone->on_cleanup == memc->on_cleanup);
221 assert(clone->on_clone == memc->on_clone);
222 assert(clone->poll_timeout == memc->poll_timeout);
223 assert(clone->rcv_timeout == memc->rcv_timeout);
224 assert(clone->recv_size == memc->recv_size);
225 assert(clone->retry_timeout == memc->retry_timeout);
226 assert(clone->send_size == memc->send_size);
227 assert(clone->server_failure_limit == memc->server_failure_limit);
228 assert(clone->snd_timeout == memc->snd_timeout);
229 assert(clone->user_data == memc->user_data);
230
231 memcached_free(clone);
232 }
233
234 /* Can we init from struct? */
235 {
236 memcached_st declared_clone;
237 memcached_st *clone;
238 memset(&declared_clone, 0 , sizeof(memcached_st));
239 clone= memcached_clone(&declared_clone, NULL);
240 assert(clone);
241 memcached_free(clone);
242 }
243
244 /* Can we init from struct? */
245 {
246 memcached_st declared_clone;
247 memcached_st *clone;
248 memset(&declared_clone, 0 , sizeof(memcached_st));
249 clone= memcached_clone(&declared_clone, memc);
250 assert(clone);
251 memcached_free(clone);
252 }
253
254 return 0;
255 }
256
257 static test_return connection_test(memcached_st *memc)
258 {
259 memcached_return rc;
260
261 rc= memcached_server_add_with_weight(memc, "localhost", 0, 0);
262 assert(rc == MEMCACHED_SUCCESS);
263
264 return 0;
265 }
266
267 static test_return error_test(memcached_st *memc)
268 {
269 memcached_return rc;
270
271 for (rc= MEMCACHED_SUCCESS; rc < MEMCACHED_MAXIMUM_RETURN; rc++)
272 {
273 printf("Error %d -> %s\n", rc, memcached_strerror(memc, rc));
274 }
275
276 return 0;
277 }
278
279 static test_return set_test(memcached_st *memc)
280 {
281 memcached_return rc;
282 char *key= "foo";
283 char *value= "when we sanitize";
284
285 rc= memcached_set(memc, key, strlen(key),
286 value, strlen(value),
287 (time_t)0, (uint32_t)0);
288 assert(rc == MEMCACHED_SUCCESS || rc == MEMCACHED_BUFFERED);
289
290 return 0;
291 }
292
293 static test_return append_test(memcached_st *memc)
294 {
295 memcached_return rc;
296 char *key= "fig";
297 char *value= "we";
298 size_t value_length;
299 uint32_t flags;
300
301 rc= memcached_flush(memc, 0);
302 assert(rc == MEMCACHED_SUCCESS);
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);
308
309 rc= memcached_append(memc, key, strlen(key),
310 " the", strlen(" the"),
311 (time_t)0, (uint32_t)0);
312 assert(rc == MEMCACHED_SUCCESS);
313
314 rc= memcached_append(memc, key, strlen(key),
315 " people", strlen(" people"),
316 (time_t)0, (uint32_t)0);
317 assert(rc == MEMCACHED_SUCCESS);
318
319 value= memcached_get(memc, key, strlen(key),
320 &value_length, &flags, &rc);
321 assert(!memcmp(value, "we the people", strlen("we the people")));
322 assert(strlen("we the people") == value_length);
323 assert(rc == MEMCACHED_SUCCESS);
324 free(value);
325
326 return 0;
327 }
328
329 static test_return append_binary_test(memcached_st *memc)
330 {
331 memcached_return rc;
332 char *key= "numbers";
333 unsigned int *store_ptr;
334 unsigned int store_list[] = { 23, 56, 499, 98, 32847, 0 };
335 char *value;
336 size_t value_length;
337 uint32_t flags;
338 unsigned int x;
339
340 rc= memcached_flush(memc, 0);
341 assert(rc == MEMCACHED_SUCCESS);
342
343 rc= memcached_set(memc,
344 key, strlen(key),
345 NULL, 0,
346 (time_t)0, (uint32_t)0);
347 assert(rc == MEMCACHED_SUCCESS);
348
349 for (x= 0; store_list[x] ; x++)
350 {
351 rc= memcached_append(memc,
352 key, strlen(key),
353 (char *)&store_list[x], sizeof(unsigned int),
354 (time_t)0, (uint32_t)0);
355 assert(rc == MEMCACHED_SUCCESS);
356 }
357
358 value= memcached_get(memc, key, strlen(key),
359 &value_length, &flags, &rc);
360 assert((value_length == (sizeof(unsigned int) * x)));
361 assert(rc == MEMCACHED_SUCCESS);
362
363 store_ptr= (unsigned int *)value;
364 x= 0;
365 while ((size_t)store_ptr < (size_t)(value + value_length))
366 {
367 assert(*store_ptr == store_list[x++]);
368 store_ptr++;
369 }
370 free(value);
371
372 return 0;
373 }
374
375 static test_return cas2_test(memcached_st *memc)
376 {
377 memcached_return rc;
378 char *keys[]= {"fudge", "son", "food"};
379 size_t key_length[]= {5, 3, 4};
380 char *value= "we the people";
381 size_t value_length= strlen("we the people");
382 unsigned int x;
383 memcached_result_st results_obj;
384 memcached_result_st *results;
385 unsigned int set= 1;
386
387 rc= memcached_flush(memc, 0);
388 assert(rc == MEMCACHED_SUCCESS);
389
390 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_SUPPORT_CAS, set);
391
392 for (x= 0; x < 3; x++)
393 {
394 rc= memcached_set(memc, keys[x], key_length[x],
395 keys[x], key_length[x],
396 (time_t)50, (uint32_t)9);
397 assert(rc == MEMCACHED_SUCCESS);
398 }
399
400 rc= memcached_mget(memc, keys, key_length, 3);
401
402 results= memcached_result_create(memc, &results_obj);
403
404 results= memcached_fetch_result(memc, &results_obj, &rc);
405 assert(results);
406 assert(results->cas);
407 assert(rc == MEMCACHED_SUCCESS);
408 WATCHPOINT_ASSERT(memcached_result_cas(results));
409
410 assert(!memcmp(value, "we the people", strlen("we the people")));
411 assert(strlen("we the people") == value_length);
412 assert(rc == MEMCACHED_SUCCESS);
413
414 memcached_result_free(&results_obj);
415
416 return 0;
417 }
418
419 static test_return cas_test(memcached_st *memc)
420 {
421 memcached_return rc;
422 const char *key= "fun";
423 size_t key_length= strlen(key);
424 const char *value= "we the people";
425 char* keys[2] = { (char*)key, NULL };
426 size_t keylengths[2] = { strlen(key), 0 };
427 size_t value_length= strlen(value);
428 const char *value2= "change the value";
429 size_t value2_length= strlen(value2);
430
431 memcached_result_st results_obj;
432 memcached_result_st *results;
433 unsigned int set= 1;
434
435 rc= memcached_flush(memc, 0);
436 assert(rc == MEMCACHED_SUCCESS);
437
438 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_SUPPORT_CAS, set);
439
440 rc= memcached_set(memc, key, strlen(key),
441 value, strlen(value),
442 (time_t)0, (uint32_t)0);
443 assert(rc == MEMCACHED_SUCCESS);
444
445 rc= memcached_mget(memc, keys, keylengths, 1);
446
447 results= memcached_result_create(memc, &results_obj);
448
449 results= memcached_fetch_result(memc, &results_obj, &rc);
450 assert(results);
451 assert(rc == MEMCACHED_SUCCESS);
452 WATCHPOINT_ASSERT(memcached_result_cas(results));
453 assert(!memcmp(value, memcached_result_value(results), value_length));
454 assert(strlen(memcached_result_value(results)) == value_length);
455 assert(rc == MEMCACHED_SUCCESS);
456 uint64_t cas = memcached_result_cas(results);
457
458 #if 0
459 results= memcached_fetch_result(memc, &results_obj, &rc);
460 assert(rc == MEMCACHED_END);
461 assert(results == NULL);
462 #endif
463
464 rc= memcached_cas(memc, key, key_length, value2, value2_length, 0, 0, cas);
465 assert(rc == MEMCACHED_SUCCESS);
466
467 /*
468 * The item will have a new cas value, so try to set it again with the old
469 * value. This should fail!
470 */
471 rc= memcached_cas(memc, key, key_length, value2, value2_length, 0, 0, cas);
472 assert(rc == MEMCACHED_DATA_EXISTS);
473
474 memcached_result_free(&results_obj);
475
476 return 0;
477 }
478
479 static test_return prepend_test(memcached_st *memc)
480 {
481 memcached_return rc;
482 char *key= "fig";
483 char *value= "people";
484 size_t value_length;
485 uint32_t flags;
486
487 rc= memcached_flush(memc, 0);
488 assert(rc == MEMCACHED_SUCCESS);
489
490 rc= memcached_set(memc, key, strlen(key),
491 value, strlen(value),
492 (time_t)0, (uint32_t)0);
493 assert(rc == MEMCACHED_SUCCESS);
494
495 rc= memcached_prepend(memc, key, strlen(key),
496 "the ", strlen("the "),
497 (time_t)0, (uint32_t)0);
498 assert(rc == MEMCACHED_SUCCESS);
499
500 rc= memcached_prepend(memc, key, strlen(key),
501 "we ", strlen("we "),
502 (time_t)0, (uint32_t)0);
503 assert(rc == MEMCACHED_SUCCESS);
504
505 value= memcached_get(memc, key, strlen(key),
506 &value_length, &flags, &rc);
507 assert(!memcmp(value, "we the people", strlen("we the people")));
508 assert(strlen("we the people") == value_length);
509 assert(rc == MEMCACHED_SUCCESS);
510 free(value);
511
512 return 0;
513 }
514
515 /*
516 Set the value, then quit to make sure it is flushed.
517 Come back in and test that add fails.
518 */
519 static test_return add_test(memcached_st *memc)
520 {
521 memcached_return rc;
522 char *key= "foo";
523 char *value= "when we sanitize";
524 unsigned long long setting_value;
525
526 setting_value= memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_NO_BLOCK);
527
528 rc= memcached_set(memc, key, strlen(key),
529 value, strlen(value),
530 (time_t)0, (uint32_t)0);
531 assert(rc == MEMCACHED_SUCCESS || rc == MEMCACHED_BUFFERED);
532 memcached_quit(memc);
533 rc= memcached_add(memc, key, strlen(key),
534 value, strlen(value),
535 (time_t)0, (uint32_t)0);
536
537 /* Too many broken OS'es have broken loopback in async, so we can't be sure of the result */
538 if (setting_value)
539 assert(rc == MEMCACHED_NOTSTORED || rc == MEMCACHED_STORED);
540 else
541 assert(rc == MEMCACHED_NOTSTORED || rc == MEMCACHED_DATA_EXISTS);
542
543 return 0;
544 }
545
546 static test_return add_wrapper(memcached_st *memc)
547 {
548 unsigned int x;
549
550 for (x= 0; x < 10000; x++)
551 add_test(memc);
552
553 return 0;
554 }
555
556 static test_return replace_test(memcached_st *memc)
557 {
558 memcached_return rc;
559 char *key= "foo";
560 char *value= "when we sanitize";
561 char *original= "first we insert some data";
562
563 rc= memcached_set(memc, key, strlen(key),
564 original, strlen(original),
565 (time_t)0, (uint32_t)0);
566 assert(rc == MEMCACHED_SUCCESS || rc == MEMCACHED_BUFFERED);
567
568 rc= memcached_replace(memc, key, strlen(key),
569 value, strlen(value),
570 (time_t)0, (uint32_t)0);
571 assert(rc == MEMCACHED_SUCCESS);
572
573 return 0;
574 }
575
576 static test_return delete_test(memcached_st *memc)
577 {
578 memcached_return rc;
579 char *key= "foo";
580 char *value= "when we sanitize";
581
582 rc= memcached_set(memc, key, strlen(key),
583 value, strlen(value),
584 (time_t)0, (uint32_t)0);
585 assert(rc == MEMCACHED_SUCCESS || rc == MEMCACHED_BUFFERED);
586
587 rc= memcached_delete(memc, key, strlen(key), (time_t)0);
588 assert(rc == MEMCACHED_SUCCESS || rc == MEMCACHED_BUFFERED);
589
590 return 0;
591 }
592
593 static test_return flush_test(memcached_st *memc)
594 {
595 memcached_return rc;
596
597 rc= memcached_flush(memc, 0);
598 assert(rc == MEMCACHED_SUCCESS);
599
600 return 0;
601 }
602
603 static memcached_return server_function(memcached_st *ptr __attribute__((unused)),
604 memcached_server_st *server __attribute__((unused)),
605 void *context __attribute__((unused)))
606 {
607 /* Do Nothing */
608
609 return MEMCACHED_SUCCESS;
610 }
611
612 static test_return memcached_server_cursor_test(memcached_st *memc)
613 {
614 char *context= "foo bad";
615 memcached_server_function callbacks[1];
616
617 callbacks[0]= server_function;
618 memcached_server_cursor(memc, callbacks, context, 1);
619
620 return 0;
621 }
622
623 static test_return bad_key_test(memcached_st *memc)
624 {
625 memcached_return rc;
626 char *key= "foo bad";
627 char *string;
628 size_t string_length;
629 uint32_t flags;
630 memcached_st *clone;
631 unsigned int set= 1;
632 size_t max_keylen= 0xffff;
633
634 clone= memcached_clone(NULL, memc);
635 assert(clone);
636
637 rc= memcached_behavior_set(clone, MEMCACHED_BEHAVIOR_VERIFY_KEY, set);
638 assert(rc == MEMCACHED_SUCCESS);
639
640 /* All keys are valid in the binary protocol (except for length) */
641 if (memcached_behavior_get(clone, MEMCACHED_BEHAVIOR_BINARY_PROTOCOL) == 0)
642 {
643 string= memcached_get(clone, key, strlen(key),
644 &string_length, &flags, &rc);
645 assert(rc == MEMCACHED_BAD_KEY_PROVIDED);
646 assert(string_length == 0);
647 assert(!string);
648
649 set= 0;
650 rc= memcached_behavior_set(clone, MEMCACHED_BEHAVIOR_VERIFY_KEY, set);
651 assert(rc == MEMCACHED_SUCCESS);
652 string= memcached_get(clone, key, strlen(key),
653 &string_length, &flags, &rc);
654 assert(rc == MEMCACHED_NOTFOUND);
655 assert(string_length == 0);
656 assert(!string);
657
658 /* Test multi key for bad keys */
659 char *keys[] = { "GoodKey", "Bad Key", "NotMine" };
660 size_t key_lengths[] = { 7, 7, 7 };
661 set= 1;
662 rc= memcached_behavior_set(clone, MEMCACHED_BEHAVIOR_VERIFY_KEY, set);
663 assert(rc == MEMCACHED_SUCCESS);
664
665 rc= memcached_mget(clone, keys, key_lengths, 3);
666 assert(rc == MEMCACHED_BAD_KEY_PROVIDED);
667
668 rc= memcached_mget_by_key(clone, "foo daddy", 9, keys, key_lengths, 1);
669 assert(rc == MEMCACHED_BAD_KEY_PROVIDED);
670
671 max_keylen= 250;
672
673 /* The following test should be moved to the end of this function when the
674 memcached server is updated to allow max size length of the keys in the
675 binary protocol
676 */
677 rc= memcached_callback_set(clone, MEMCACHED_CALLBACK_PREFIX_KEY, NULL);
678 assert(rc == MEMCACHED_SUCCESS);
679
680 char *longkey= malloc(max_keylen + 1);
681 if (longkey != NULL)
682 {
683 memset(longkey, 'a', max_keylen + 1);
684 string= memcached_get(clone, longkey, max_keylen,
685 &string_length, &flags, &rc);
686 assert(rc == MEMCACHED_NOTFOUND);
687 assert(string_length == 0);
688 assert(!string);
689
690 string= memcached_get(clone, longkey, max_keylen + 1,
691 &string_length, &flags, &rc);
692 assert(rc == MEMCACHED_BAD_KEY_PROVIDED);
693 assert(string_length == 0);
694 assert(!string);
695
696 free(longkey);
697 }
698 }
699
700 /* Make sure zero length keys are marked as bad */
701 set= 1;
702 rc= memcached_behavior_set(clone, MEMCACHED_BEHAVIOR_VERIFY_KEY, set);
703 assert(rc == MEMCACHED_SUCCESS);
704 string= memcached_get(clone, key, 0,
705 &string_length, &flags, &rc);
706 assert(rc == MEMCACHED_BAD_KEY_PROVIDED);
707 assert(string_length == 0);
708 assert(!string);
709
710 memcached_free(clone);
711
712 return 0;
713 }
714
715 #define READ_THROUGH_VALUE "set for me"
716 static memcached_return read_through_trigger(memcached_st *memc __attribute__((unused)),
717 char *key __attribute__((unused)),
718 size_t key_length __attribute__((unused)),
719 memcached_result_st *result)
720 {
721
722 return memcached_result_set_value(result, READ_THROUGH_VALUE, strlen(READ_THROUGH_VALUE));
723 }
724
725 static test_return read_through(memcached_st *memc)
726 {
727 memcached_return rc;
728 char *key= "foo";
729 char *string;
730 size_t string_length;
731 uint32_t flags;
732
733 string= memcached_get(memc, key, strlen(key),
734 &string_length, &flags, &rc);
735
736 assert(rc == MEMCACHED_NOTFOUND);
737 assert(string_length == 0);
738 assert(!string);
739
740 rc= memcached_callback_set(memc, MEMCACHED_CALLBACK_GET_FAILURE, (void *)read_through_trigger);
741 assert(rc == MEMCACHED_SUCCESS);
742
743 string= memcached_get(memc, key, strlen(key),
744 &string_length, &flags, &rc);
745
746 assert(rc == MEMCACHED_SUCCESS);
747 assert(string_length == strlen(READ_THROUGH_VALUE));
748 assert(!strcmp(READ_THROUGH_VALUE, string));
749 free(string);
750
751 string= memcached_get(memc, key, strlen(key),
752 &string_length, &flags, &rc);
753
754 assert(rc == MEMCACHED_SUCCESS);
755 assert(string_length == strlen(READ_THROUGH_VALUE));
756 assert(!strcmp(READ_THROUGH_VALUE, string));
757 free(string);
758
759 return 0;
760 }
761
762 static memcached_return delete_trigger(memcached_st *ptr __attribute__((unused)),
763 const char *key,
764 size_t key_length __attribute__((unused)))
765 {
766 assert(key);
767
768 return MEMCACHED_SUCCESS;
769 }
770
771 static test_return delete_through(memcached_st *memc)
772 {
773 memcached_trigger_delete_key callback;
774 memcached_return rc;
775
776 callback= delete_trigger;
777
778 rc= memcached_callback_set(memc, MEMCACHED_CALLBACK_DELETE_TRIGGER, (void*)callback);
779 assert(rc == MEMCACHED_SUCCESS);
780
781 return 0;
782 }
783
784 static test_return get_test(memcached_st *memc)
785 {
786 memcached_return rc;
787 char *key= "foo";
788 char *string;
789 size_t string_length;
790 uint32_t flags;
791
792 rc= memcached_delete(memc, key, strlen(key), (time_t)0);
793 assert(rc == MEMCACHED_BUFFERED || rc == MEMCACHED_NOTFOUND);
794
795 string= memcached_get(memc, key, strlen(key),
796 &string_length, &flags, &rc);
797
798 assert(rc == MEMCACHED_NOTFOUND);
799 assert(string_length == 0);
800 assert(!string);
801
802 return 0;
803 }
804
805 static test_return get_test2(memcached_st *memc)
806 {
807 memcached_return rc;
808 char *key= "foo";
809 char *value= "when we sanitize";
810 char *string;
811 size_t string_length;
812 uint32_t flags;
813
814 rc= memcached_set(memc, key, strlen(key),
815 value, strlen(value),
816 (time_t)0, (uint32_t)0);
817 assert(rc == MEMCACHED_SUCCESS || rc == MEMCACHED_BUFFERED);
818
819 string= memcached_get(memc, key, strlen(key),
820 &string_length, &flags, &rc);
821
822 assert(string);
823 assert(rc == MEMCACHED_SUCCESS);
824 assert(string_length == strlen(value));
825 assert(!memcmp(string, value, string_length));
826
827 free(string);
828
829 return 0;
830 }
831
832 static test_return set_test2(memcached_st *memc)
833 {
834 memcached_return rc;
835 char *key= "foo";
836 char *value= "train in the brain";
837 size_t value_length= strlen(value);
838 unsigned int x;
839
840 for (x= 0; x < 10; x++)
841 {
842 rc= memcached_set(memc, key, strlen(key),
843 value, value_length,
844 (time_t)0, (uint32_t)0);
845 assert(rc == MEMCACHED_SUCCESS || rc == MEMCACHED_BUFFERED);
846 }
847
848 return 0;
849 }
850
851 static test_return set_test3(memcached_st *memc)
852 {
853 memcached_return rc;
854 char *key= "foo";
855 char *value;
856 size_t value_length= 8191;
857 unsigned int x;
858
859 value = (char*)malloc(value_length);
860 assert(value);
861
862 for (x= 0; x < value_length; x++)
863 value[x] = (char) (x % 127);
864
865 for (x= 0; x < 1; x++)
866 {
867 rc= memcached_set(memc, key, strlen(key),
868 value, value_length,
869 (time_t)0, (uint32_t)0);
870 assert(rc == MEMCACHED_SUCCESS || rc == MEMCACHED_BUFFERED);
871 }
872
873 free(value);
874
875 return 0;
876 }
877
878 static test_return get_test3(memcached_st *memc)
879 {
880 memcached_return rc;
881 char *key= "foo";
882 char *value;
883 size_t value_length= 8191;
884 char *string;
885 size_t string_length;
886 uint32_t flags;
887 uint32_t x;
888
889 value = (char*)malloc(value_length);
890 assert(value);
891
892 for (x= 0; x < value_length; x++)
893 value[x] = (char) (x % 127);
894
895 rc= memcached_set(memc, key, strlen(key),
896 value, value_length,
897 (time_t)0, (uint32_t)0);
898 assert(rc == MEMCACHED_SUCCESS || rc == MEMCACHED_BUFFERED);
899
900 string= memcached_get(memc, key, strlen(key),
901 &string_length, &flags, &rc);
902
903 assert(rc == MEMCACHED_SUCCESS);
904 assert(string);
905 assert(string_length == value_length);
906 assert(!memcmp(string, value, string_length));
907
908 free(string);
909 free(value);
910
911 return 0;
912 }
913
914 static test_return get_test4(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 for (x= 0; x < 10; x++)
937 {
938 string= memcached_get(memc, key, strlen(key),
939 &string_length, &flags, &rc);
940
941 assert(rc == MEMCACHED_SUCCESS);
942 assert(string);
943 assert(string_length == value_length);
944 assert(!memcmp(string, value, string_length));
945 free(string);
946 }
947
948 free(value);
949
950 return 0;
951 }
952
953 /* Do not copy the style of this code, I just access hosts to testthis function */
954 static test_return stats_servername_test(memcached_st *memc)
955 {
956 memcached_return rc;
957 memcached_stat_st stat;
958 rc= memcached_stat_servername(&stat, NULL,
959 memc->hosts[0].hostname,
960 memc->hosts[0].port);
961
962 return 0;
963 }
964
965 static test_return increment_test(memcached_st *memc)
966 {
967 uint64_t new_number;
968 memcached_return rc;
969 char *key= "number";
970 char *value= "0";
971
972 rc= memcached_set(memc, key, strlen(key),
973 value, strlen(value),
974 (time_t)0, (uint32_t)0);
975 assert(rc == MEMCACHED_SUCCESS || rc == MEMCACHED_BUFFERED);
976
977 rc= memcached_increment(memc, key, strlen(key),
978 1, &new_number);
979 assert(rc == MEMCACHED_SUCCESS);
980 assert(new_number == 1);
981
982 rc= memcached_increment(memc, key, strlen(key),
983 1, &new_number);
984 assert(rc == MEMCACHED_SUCCESS);
985 assert(new_number == 2);
986
987 return 0;
988 }
989
990 static test_return decrement_test(memcached_st *memc)
991 {
992 uint64_t new_number;
993 memcached_return rc;
994 char *key= "number";
995 char *value= "3";
996
997 rc= memcached_set(memc, key, strlen(key),
998 value, strlen(value),
999 (time_t)0, (uint32_t)0);
1000 assert(rc == MEMCACHED_SUCCESS || rc == MEMCACHED_BUFFERED);
1001
1002 rc= memcached_decrement(memc, key, strlen(key),
1003 1, &new_number);
1004 assert(rc == MEMCACHED_SUCCESS);
1005 assert(new_number == 2);
1006
1007 rc= memcached_decrement(memc, key, strlen(key),
1008 1, &new_number);
1009 assert(rc == MEMCACHED_SUCCESS);
1010 assert(new_number == 1);
1011
1012 return 0;
1013 }
1014
1015 static test_return quit_test(memcached_st *memc)
1016 {
1017 memcached_return rc;
1018 char *key= "fudge";
1019 char *value= "sanford and sun";
1020
1021 rc= memcached_set(memc, key, strlen(key),
1022 value, strlen(value),
1023 (time_t)10, (uint32_t)3);
1024 assert(rc == MEMCACHED_SUCCESS || rc == MEMCACHED_BUFFERED);
1025 memcached_quit(memc);
1026
1027 rc= memcached_set(memc, key, strlen(key),
1028 value, strlen(value),
1029 (time_t)50, (uint32_t)9);
1030 assert(rc == MEMCACHED_SUCCESS || rc == MEMCACHED_BUFFERED);
1031
1032 return 0;
1033 }
1034
1035 static test_return mget_result_test(memcached_st *memc)
1036 {
1037 memcached_return rc;
1038 char *keys[]= {"fudge", "son", "food"};
1039 size_t key_length[]= {5, 3, 4};
1040 unsigned int x;
1041
1042 memcached_result_st results_obj;
1043 memcached_result_st *results;
1044
1045 results= memcached_result_create(memc, &results_obj);
1046 assert(results);
1047 assert(&results_obj == results);
1048
1049 /* We need to empty the server before continueing test */
1050 rc= memcached_flush(memc, 0);
1051 assert(rc == MEMCACHED_SUCCESS);
1052
1053 rc= memcached_mget(memc, keys, key_length, 3);
1054 assert(rc == MEMCACHED_SUCCESS);
1055
1056 while ((results= memcached_fetch_result(memc, &results_obj, &rc)) != NULL)
1057 {
1058 assert(results);
1059 }
1060
1061 while ((results= memcached_fetch_result(memc, &results_obj, &rc)) != NULL)
1062 assert(!results);
1063 assert(rc == MEMCACHED_END);
1064
1065 for (x= 0; x < 3; x++)
1066 {
1067 rc= memcached_set(memc, keys[x], key_length[x],
1068 keys[x], key_length[x],
1069 (time_t)50, (uint32_t)9);
1070 assert(rc == MEMCACHED_SUCCESS || rc == MEMCACHED_BUFFERED);
1071 }
1072
1073 rc= memcached_mget(memc, keys, key_length, 3);
1074 assert(rc == MEMCACHED_SUCCESS);
1075
1076 while ((results= memcached_fetch_result(memc, &results_obj, &rc)))
1077 {
1078 assert(results);
1079 assert(&results_obj == results);
1080 assert(rc == MEMCACHED_SUCCESS);
1081 assert(memcached_result_key_length(results) == memcached_result_length(results));
1082 assert(!memcmp(memcached_result_key_value(results),
1083 memcached_result_value(results),
1084 memcached_result_length(results)));
1085 }
1086
1087 memcached_result_free(&results_obj);
1088
1089 return 0;
1090 }
1091
1092 static test_return mget_result_alloc_test(memcached_st *memc)
1093 {
1094 memcached_return rc;
1095 char *keys[]= {"fudge", "son", "food"};
1096 size_t key_length[]= {5, 3, 4};
1097 unsigned int x;
1098
1099 memcached_result_st *results;
1100
1101 /* We need to empty the server before continueing test */
1102 rc= memcached_flush(memc, 0);
1103 assert(rc == MEMCACHED_SUCCESS);
1104
1105 rc= memcached_mget(memc, keys, key_length, 3);
1106 assert(rc == MEMCACHED_SUCCESS);
1107
1108 while ((results= memcached_fetch_result(memc, NULL, &rc)) != NULL)
1109 {
1110 assert(results);
1111 }
1112 assert(!results);
1113 assert(rc == MEMCACHED_END);
1114
1115 for (x= 0; x < 3; x++)
1116 {
1117 rc= memcached_set(memc, keys[x], key_length[x],
1118 keys[x], key_length[x],
1119 (time_t)50, (uint32_t)9);
1120 assert(rc == MEMCACHED_SUCCESS || rc == MEMCACHED_BUFFERED);
1121 }
1122
1123 rc= memcached_mget(memc, keys, key_length, 3);
1124 assert(rc == MEMCACHED_SUCCESS);
1125
1126 x= 0;
1127 while ((results= memcached_fetch_result(memc, NULL, &rc)))
1128 {
1129 assert(results);
1130 assert(rc == MEMCACHED_SUCCESS);
1131 assert(memcached_result_key_length(results) == memcached_result_length(results));
1132 assert(!memcmp(memcached_result_key_value(results),
1133 memcached_result_value(results),
1134 memcached_result_length(results)));
1135 memcached_result_free(results);
1136 x++;
1137 }
1138
1139 return 0;
1140 }
1141
1142 /* Count the results */
1143 static memcached_return callback_counter(memcached_st *ptr __attribute__((unused)),
1144 memcached_result_st *result __attribute__((unused)),
1145 void *context)
1146 {
1147 unsigned int *counter= (unsigned int *)context;
1148
1149 *counter= *counter + 1;
1150
1151 return MEMCACHED_SUCCESS;
1152 }
1153
1154 static test_return mget_result_function(memcached_st *memc)
1155 {
1156 memcached_return rc;
1157 char *keys[]= {"fudge", "son", "food"};
1158 size_t key_length[]= {5, 3, 4};
1159 unsigned int x;
1160 unsigned int counter;
1161 memcached_execute_function callbacks[1];
1162
1163 /* We need to empty the server before continueing test */
1164 rc= memcached_flush(memc, 0);
1165 for (x= 0; x < 3; x++)
1166 {
1167 rc= memcached_set(memc, keys[x], key_length[x],
1168 keys[x], key_length[x],
1169 (time_t)50, (uint32_t)9);
1170 assert(rc == MEMCACHED_SUCCESS || rc == MEMCACHED_BUFFERED);
1171 }
1172
1173 rc= memcached_mget(memc, keys, key_length, 3);
1174 assert(rc == MEMCACHED_SUCCESS);
1175
1176 callbacks[0]= &callback_counter;
1177 counter= 0;
1178 rc= memcached_fetch_execute(memc, callbacks, (void *)&counter, 1);
1179
1180 assert(counter == 3);
1181
1182 return 0;
1183 }
1184
1185 static test_return mget_test(memcached_st *memc)
1186 {
1187 memcached_return rc;
1188 char *keys[]= {"fudge", "son", "food"};
1189 size_t key_length[]= {5, 3, 4};
1190 unsigned int x;
1191 uint32_t flags;
1192
1193 char return_key[MEMCACHED_MAX_KEY];
1194 size_t return_key_length;
1195 char *return_value;
1196 size_t return_value_length;
1197
1198 /* We need to empty the server before continueing test */
1199 rc= memcached_flush(memc, 0);
1200 assert(rc == MEMCACHED_SUCCESS);
1201
1202 rc= memcached_mget(memc, keys, key_length, 3);
1203 assert(rc == MEMCACHED_SUCCESS);
1204
1205 while ((return_value= memcached_fetch(memc, return_key, &return_key_length,
1206 &return_value_length, &flags, &rc)) != NULL)
1207 {
1208 assert(return_value);
1209 }
1210 assert(!return_value);
1211 assert(return_value_length == 0);
1212 assert(rc == MEMCACHED_END);
1213
1214 for (x= 0; x < 3; x++)
1215 {
1216 rc= memcached_set(memc, keys[x], key_length[x],
1217 keys[x], key_length[x],
1218 (time_t)50, (uint32_t)9);
1219 assert(rc == MEMCACHED_SUCCESS || rc == MEMCACHED_BUFFERED);
1220 }
1221
1222 rc= memcached_mget(memc, keys, key_length, 3);
1223 assert(rc == MEMCACHED_SUCCESS);
1224
1225 x= 0;
1226 while ((return_value= memcached_fetch(memc, return_key, &return_key_length,
1227 &return_value_length, &flags, &rc)))
1228 {
1229 assert(return_value);
1230 assert(rc == MEMCACHED_SUCCESS);
1231 assert(return_key_length == return_value_length);
1232 assert(!memcmp(return_value, return_key, return_value_length));
1233 free(return_value);
1234 x++;
1235 }
1236
1237 return 0;
1238 }
1239
1240 static test_return get_stats_keys(memcached_st *memc)
1241 {
1242 char **list;
1243 char **ptr;
1244 memcached_stat_st stat;
1245 memcached_return rc;
1246
1247 list= memcached_stat_get_keys(memc, &stat, &rc);
1248 assert(rc == MEMCACHED_SUCCESS);
1249 for (ptr= list; *ptr; ptr++)
1250 assert(*ptr);
1251 fflush(stdout);
1252
1253 free(list);
1254
1255 return 0;
1256 }
1257
1258 static test_return version_string_test(memcached_st *memc __attribute__((unused)))
1259 {
1260 const char *version_string;
1261
1262 version_string= memcached_lib_version();
1263
1264 assert(!strcmp(version_string, LIBMEMCACHED_VERSION_STRING));
1265
1266 return 0;
1267 }
1268
1269 static test_return get_stats(memcached_st *memc)
1270 {
1271 unsigned int x;
1272 char **list;
1273 char **ptr;
1274 memcached_return rc;
1275 memcached_stat_st *stat;
1276
1277 stat= memcached_stat(memc, NULL, &rc);
1278 assert(rc == MEMCACHED_SUCCESS);
1279
1280 assert(rc == MEMCACHED_SUCCESS);
1281 assert(stat);
1282
1283 for (x= 0; x < memcached_server_count(memc); x++)
1284 {
1285 list= memcached_stat_get_keys(memc, stat+x, &rc);
1286 assert(rc == MEMCACHED_SUCCESS);
1287 for (ptr= list; *ptr; ptr++);
1288
1289 free(list);
1290 }
1291
1292 memcached_stat_free(NULL, stat);
1293
1294 return 0;
1295 }
1296
1297 static test_return add_host_test(memcached_st *memc)
1298 {
1299 unsigned int x;
1300 memcached_server_st *servers;
1301 memcached_return rc;
1302 char servername[]= "0.example.com";
1303
1304 servers= memcached_server_list_append_with_weight(NULL, servername, 400, 0, &rc);
1305 assert(servers);
1306 assert(1 == memcached_server_list_count(servers));
1307
1308 for (x= 2; x < 20; x++)
1309 {
1310 char buffer[SMALL_STRING_LEN];
1311
1312 snprintf(buffer, SMALL_STRING_LEN, "%u.example.com", 400+x);
1313 servers= memcached_server_list_append_with_weight(servers, buffer, 401, 0,
1314 &rc);
1315 assert(rc == MEMCACHED_SUCCESS);
1316 assert(x == memcached_server_list_count(servers));
1317 }
1318
1319 rc= memcached_server_push(memc, servers);
1320 assert(rc == MEMCACHED_SUCCESS);
1321 rc= memcached_server_push(memc, servers);
1322 assert(rc == MEMCACHED_SUCCESS);
1323
1324 memcached_server_list_free(servers);
1325
1326 return 0;
1327 }
1328
1329 static memcached_return clone_test_callback(memcached_st *parent __attribute__((unused)), memcached_st *clone __attribute__((unused)))
1330 {
1331 return MEMCACHED_SUCCESS;
1332 }
1333
1334 static memcached_return cleanup_test_callback(memcached_st *ptr __attribute__((unused)))
1335 {
1336 return MEMCACHED_SUCCESS;
1337 }
1338
1339 static test_return callback_test(memcached_st *memc)
1340 {
1341 /* Test User Data */
1342 {
1343 int x= 5;
1344 int *test_ptr;
1345 memcached_return rc;
1346
1347 rc= memcached_callback_set(memc, MEMCACHED_CALLBACK_USER_DATA, &x);
1348 assert(rc == MEMCACHED_SUCCESS);
1349 test_ptr= (int *)memcached_callback_get(memc, MEMCACHED_CALLBACK_USER_DATA, &rc);
1350 assert(*test_ptr == x);
1351 }
1352
1353 /* Test Clone Callback */
1354 {
1355 memcached_clone_func temp_function;
1356 memcached_return rc;
1357
1358 rc= memcached_callback_set(memc, MEMCACHED_CALLBACK_CLONE_FUNCTION, (void*)clone_test_callback);
1359 assert(rc == MEMCACHED_SUCCESS);
1360 temp_function= (memcached_clone_func)memcached_callback_get(memc, MEMCACHED_CALLBACK_CLONE_FUNCTION, &rc);
1361 assert(temp_function == clone_test_callback);
1362 }
1363
1364 /* Test Cleanup Callback */
1365 {
1366 memcached_cleanup_func temp_function;
1367 memcached_return rc;
1368
1369 rc= memcached_callback_set(memc, MEMCACHED_CALLBACK_CLONE_FUNCTION, (void*)cleanup_test_callback);
1370 assert(rc == MEMCACHED_SUCCESS);
1371 temp_function= (memcached_cleanup_func)memcached_callback_get(memc, MEMCACHED_CALLBACK_CLONE_FUNCTION, &rc);
1372 assert(temp_function == cleanup_test_callback);
1373 }
1374
1375 return 0;
1376 }
1377
1378 /* We don't test the behavior itself, we test the switches */
1379 static test_return behavior_test(memcached_st *memc)
1380 {
1381 uint64_t value;
1382 uint32_t set= 1;
1383
1384 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_NO_BLOCK, set);
1385 value= memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_NO_BLOCK);
1386 assert(value == 1);
1387
1388 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_TCP_NODELAY, set);
1389 value= memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_TCP_NODELAY);
1390 assert(value == 1);
1391
1392 set= MEMCACHED_HASH_MD5;
1393 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_HASH, set);
1394 value= memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_HASH);
1395 assert(value == MEMCACHED_HASH_MD5);
1396
1397 set= 0;
1398
1399 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_NO_BLOCK, set);
1400 value= memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_NO_BLOCK);
1401 assert(value == 0);
1402
1403 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_TCP_NODELAY, set);
1404 value= memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_TCP_NODELAY);
1405 assert(value == 0);
1406
1407 set= MEMCACHED_HASH_DEFAULT;
1408 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_HASH, set);
1409 value= memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_HASH);
1410 assert(value == MEMCACHED_HASH_DEFAULT);
1411
1412 set= MEMCACHED_HASH_CRC;
1413 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_HASH, set);
1414 value= memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_HASH);
1415 assert(value == MEMCACHED_HASH_CRC);
1416
1417 value= memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_SOCKET_SEND_SIZE);
1418 assert(value > 0);
1419
1420 value= memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_SOCKET_RECV_SIZE);
1421 assert(value > 0);
1422
1423 return 0;
1424 }
1425
1426 /* Test case provided by Cal Haldenbrand */
1427 static test_return user_supplied_bug1(memcached_st *memc)
1428 {
1429 unsigned int setter= 1;
1430 unsigned int x;
1431
1432 unsigned long long total= 0;
1433 uint32_t size= 0;
1434 char key[10];
1435 char randomstuff[6 * 1024];
1436 memcached_return rc;
1437
1438 memset(randomstuff, 0, 6 * 1024);
1439
1440 /* We just keep looking at the same values over and over */
1441 srandom(10);
1442
1443 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_NO_BLOCK, setter);
1444 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_TCP_NODELAY, setter);
1445
1446
1447 /* add key */
1448 for (x= 0 ; total < 20 * 1024576 ; x++ )
1449 {
1450 unsigned int j= 0;
1451
1452 size= (rand() % ( 5 * 1024 ) ) + 400;
1453 memset(randomstuff, 0, 6 * 1024);
1454 assert(size < 6 * 1024); /* Being safe here */
1455
1456 for (j= 0 ; j < size ;j++)
1457 randomstuff[j] = (char) (rand() % 26) + 97;
1458
1459 total += size;
1460 sprintf(key, "%d", x);
1461 rc = memcached_set(memc, key, strlen(key),
1462 randomstuff, strlen(randomstuff), 10, 0);
1463 assert(rc == MEMCACHED_SUCCESS || rc == MEMCACHED_BUFFERED);
1464 /* If we fail, lets try again */
1465 if (rc != MEMCACHED_SUCCESS && rc != MEMCACHED_BUFFERED)
1466 rc = memcached_set(memc, key, strlen(key),
1467 randomstuff, strlen(randomstuff), 10, 0);
1468 assert(rc == MEMCACHED_SUCCESS || rc == MEMCACHED_BUFFERED);
1469 }
1470
1471 return 0;
1472 }
1473
1474 /* Test case provided by Cal Haldenbrand */
1475 static test_return user_supplied_bug2(memcached_st *memc)
1476 {
1477 int errors;
1478 unsigned int setter;
1479 unsigned int x;
1480 unsigned long long total;
1481
1482 setter= 1;
1483 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_NO_BLOCK, setter);
1484 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_TCP_NODELAY, setter);
1485 #ifdef NOT_YET
1486 setter = 20 * 1024576;
1487 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_SOCKET_SEND_SIZE, setter);
1488 setter = 20 * 1024576;
1489 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_SOCKET_RECV_SIZE, setter);
1490 getter = memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_SOCKET_SEND_SIZE);
1491 getter = memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_SOCKET_RECV_SIZE);
1492
1493 for (x= 0, errors= 0, total= 0 ; total < 20 * 1024576 ; x++)
1494 #endif
1495
1496 for (x= 0, errors= 0, total= 0 ; total < 24576 ; x++)
1497 {
1498 memcached_return rc= MEMCACHED_SUCCESS;
1499 char buffer[SMALL_STRING_LEN];
1500 uint32_t flags= 0;
1501 size_t val_len= 0;
1502 char *getval;
1503
1504 memset(buffer, 0, SMALL_STRING_LEN);
1505
1506 snprintf(buffer, SMALL_STRING_LEN, "%u", x);
1507 getval= memcached_get(memc, buffer, strlen(buffer),
1508 &val_len, &flags, &rc);
1509 if (rc != MEMCACHED_SUCCESS)
1510 {
1511 if (rc == MEMCACHED_NOTFOUND)
1512 errors++;
1513 else
1514 {
1515 WATCHPOINT_ERROR(rc);
1516 assert(0);
1517 }
1518
1519 continue;
1520 }
1521 total+= val_len;
1522 errors= 0;
1523 free(getval);
1524 }
1525
1526 return 0;
1527 }
1528
1529 /* Do a large mget() over all the keys we think exist */
1530 #define KEY_COUNT 3000 // * 1024576
1531 static test_return user_supplied_bug3(memcached_st *memc)
1532 {
1533 memcached_return rc;
1534 unsigned int setter;
1535 unsigned int x;
1536 char **keys;
1537 size_t key_lengths[KEY_COUNT];
1538
1539 setter= 1;
1540 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_NO_BLOCK, setter);
1541 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_TCP_NODELAY, setter);
1542 #ifdef NOT_YET
1543 setter = 20 * 1024576;
1544 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_SOCKET_SEND_SIZE, setter);
1545 setter = 20 * 1024576;
1546 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_SOCKET_RECV_SIZE, setter);
1547 getter = memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_SOCKET_SEND_SIZE);
1548 getter = memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_SOCKET_RECV_SIZE);
1549 #endif
1550
1551 keys= (char **)malloc(sizeof(char *) * KEY_COUNT);
1552 assert(keys);
1553 memset(keys, 0, (sizeof(char *) * KEY_COUNT));
1554 for (x= 0; x < KEY_COUNT; x++)
1555 {
1556 char buffer[30];
1557
1558 snprintf(buffer, 30, "%u", x);
1559 keys[x]= strdup(buffer);
1560 key_lengths[x]= strlen(keys[x]);
1561 }
1562
1563 rc= memcached_mget(memc, keys, key_lengths, KEY_COUNT);
1564 assert(rc == MEMCACHED_SUCCESS);
1565
1566 /* Turn this into a help function */
1567 {
1568 char return_key[MEMCACHED_MAX_KEY];
1569 size_t return_key_length;
1570 char *return_value;
1571 size_t return_value_length;
1572 uint32_t flags;
1573
1574 while ((return_value= memcached_fetch(memc, return_key, &return_key_length,
1575 &return_value_length, &flags, &rc)))
1576 {
1577 assert(return_value);
1578 assert(rc == MEMCACHED_SUCCESS);
1579 free(return_value);
1580 }
1581 }
1582
1583 for (x= 0; x < KEY_COUNT; x++)
1584 free(keys[x]);
1585 free(keys);
1586
1587 return 0;
1588 }
1589
1590 /* Make sure we behave properly if server list has no values */
1591 static test_return user_supplied_bug4(memcached_st *memc)
1592 {
1593 memcached_return rc;
1594 char *keys[]= {"fudge", "son", "food"};
1595 size_t key_length[]= {5, 3, 4};
1596 unsigned int x;
1597 uint32_t flags;
1598 char return_key[MEMCACHED_MAX_KEY];
1599 size_t return_key_length;
1600 char *return_value;
1601 size_t return_value_length;
1602
1603 /* Here we free everything before running a bunch of mget tests */
1604 {
1605 memcached_server_list_free(memc->hosts);
1606 memc->hosts= NULL;
1607 memc->number_of_hosts= 0;
1608 }
1609
1610
1611 /* We need to empty the server before continueing test */
1612 rc= memcached_flush(memc, 0);
1613 assert(rc == MEMCACHED_NO_SERVERS);
1614
1615 rc= memcached_mget(memc, keys, key_length, 3);
1616 assert(rc == MEMCACHED_NO_SERVERS);
1617
1618 while ((return_value= memcached_fetch(memc, return_key, &return_key_length,
1619 &return_value_length, &flags, &rc)) != NULL)
1620 {
1621 assert(return_value);
1622 }
1623 assert(!return_value);
1624 assert(return_value_length == 0);
1625 assert(rc == MEMCACHED_NO_SERVERS);
1626
1627 for (x= 0; x < 3; x++)
1628 {
1629 rc= memcached_set(memc, keys[x], key_length[x],
1630 keys[x], key_length[x],
1631 (time_t)50, (uint32_t)9);
1632 assert(rc == MEMCACHED_NO_SERVERS);
1633 }
1634
1635 rc= memcached_mget(memc, keys, key_length, 3);
1636 assert(rc == MEMCACHED_NO_SERVERS);
1637
1638 x= 0;
1639 while ((return_value= memcached_fetch(memc, return_key, &return_key_length,
1640 &return_value_length, &flags, &rc)))
1641 {
1642 assert(return_value);
1643 assert(rc == MEMCACHED_SUCCESS);
1644 assert(return_key_length == return_value_length);
1645 assert(!memcmp(return_value, return_key, return_value_length));
1646 free(return_value);
1647 x++;
1648 }
1649
1650 return 0;
1651 }
1652
1653 #define VALUE_SIZE_BUG5 1048064
1654 static test_return user_supplied_bug5(memcached_st *memc)
1655 {
1656 memcached_return rc;
1657 char *keys[]= {"036790384900", "036790384902", "036790384904", "036790384906"};
1658 size_t key_length[]= {strlen("036790384900"), strlen("036790384902"), strlen("036790384904"), strlen("036790384906")};
1659 char return_key[MEMCACHED_MAX_KEY];
1660 size_t return_key_length;
1661 char *value;
1662 size_t value_length;
1663 uint32_t flags;
1664 unsigned int count;
1665 unsigned int x;
1666 char insert_data[VALUE_SIZE_BUG5];
1667
1668 for (x= 0; x < VALUE_SIZE_BUG5; x++)
1669 insert_data[x]= rand();
1670
1671 memcached_flush(memc, 0);
1672 value= memcached_get(memc, keys[0], key_length[0],
1673 &value_length, &flags, &rc);
1674 assert(value == NULL);
1675 rc= memcached_mget(memc, keys, key_length, 4);
1676
1677 count= 0;
1678 while ((value= memcached_fetch(memc, return_key, &return_key_length,
1679 &value_length, &flags, &rc)))
1680 count++;
1681 assert(count == 0);
1682
1683 for (x= 0; x < 4; x++)
1684 {
1685 rc= memcached_set(memc, keys[x], key_length[x],
1686 insert_data, VALUE_SIZE_BUG5,
1687 (time_t)0, (uint32_t)0);
1688 assert(rc == MEMCACHED_SUCCESS);
1689 }
1690
1691 for (x= 0; x < 10; x++)
1692 {
1693 value= memcached_get(memc, keys[0], key_length[0],
1694 &value_length, &flags, &rc);
1695 assert(value);
1696 free(value);
1697
1698 rc= memcached_mget(memc, keys, key_length, 4);
1699 count= 0;
1700 while ((value= memcached_fetch(memc, return_key, &return_key_length,
1701 &value_length, &flags, &rc)))
1702 {
1703 count++;
1704 free(value);
1705 }
1706 assert(count == 4);
1707 }
1708
1709 return 0;
1710 }
1711
1712 static test_return user_supplied_bug6(memcached_st *memc)
1713 {
1714 memcached_return rc;
1715 char *keys[]= {"036790384900", "036790384902", "036790384904", "036790384906"};
1716 size_t key_length[]= {strlen("036790384900"), strlen("036790384902"), strlen("036790384904"), strlen("036790384906")};
1717 char return_key[MEMCACHED_MAX_KEY];
1718 size_t return_key_length;
1719 char *value;
1720 size_t value_length;
1721 uint32_t flags;
1722 unsigned int count;
1723 unsigned int x;
1724 char insert_data[VALUE_SIZE_BUG5];
1725
1726 for (x= 0; x < VALUE_SIZE_BUG5; x++)
1727 insert_data[x]= rand();
1728
1729 memcached_flush(memc, 0);
1730 value= memcached_get(memc, keys[0], key_length[0],
1731 &value_length, &flags, &rc);
1732 assert(value == NULL);
1733 assert(rc == MEMCACHED_NOTFOUND);
1734 rc= memcached_mget(memc, keys, key_length, 4);
1735 assert(rc == MEMCACHED_SUCCESS);
1736
1737 count= 0;
1738 while ((value= memcached_fetch(memc, return_key, &return_key_length,
1739 &value_length, &flags, &rc)))
1740 count++;
1741 assert(count == 0);
1742 assert(rc == MEMCACHED_END);
1743
1744 for (x= 0; x < 4; x++)
1745 {
1746 rc= memcached_set(memc, keys[x], key_length[x],
1747 insert_data, VALUE_SIZE_BUG5,
1748 (time_t)0, (uint32_t)0);
1749 assert(rc == MEMCACHED_SUCCESS);
1750 }
1751
1752 for (x= 0; x < 2; x++)
1753 {
1754 value= memcached_get(memc, keys[0], key_length[0],
1755 &value_length, &flags, &rc);
1756 assert(value);
1757 free(value);
1758
1759 rc= memcached_mget(memc, keys, key_length, 4);
1760 assert(rc == MEMCACHED_SUCCESS);
1761 count= 3;
1762 /* We test for purge of partial complete fetches */
1763 for (count= 3; count; count--)
1764 {
1765 value= memcached_fetch(memc, return_key, &return_key_length,
1766 &value_length, &flags, &rc);
1767 assert(rc == MEMCACHED_SUCCESS);
1768 assert(!(memcmp(value, insert_data, value_length)));
1769 assert(value_length);
1770 free(value);
1771 }
1772 }
1773
1774 return 0;
1775 }
1776
1777 static test_return user_supplied_bug8(memcached_st *memc __attribute__((unused)))
1778 {
1779 memcached_return rc;
1780 memcached_st *mine;
1781 memcached_st *clone;
1782
1783 memcached_server_st *servers;
1784 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";
1785
1786 servers= memcached_servers_parse(server_list);
1787 assert(servers);
1788
1789 mine= memcached_create(NULL);
1790 rc= memcached_server_push(mine, servers);
1791 assert(rc == MEMCACHED_SUCCESS);
1792 memcached_server_list_free(servers);
1793
1794 assert(mine);
1795 clone= memcached_clone(NULL, mine);
1796
1797 memcached_quit(mine);
1798 memcached_quit(clone);
1799
1800
1801 memcached_free(mine);
1802 memcached_free(clone);
1803
1804 return 0;
1805 }
1806
1807 /* Test flag store/retrieve */
1808 static test_return user_supplied_bug7(memcached_st *memc)
1809 {
1810 memcached_return rc;
1811 char *keys= "036790384900";
1812 size_t key_length= strlen("036790384900");
1813 char return_key[MEMCACHED_MAX_KEY];
1814 size_t return_key_length;
1815 char *value;
1816 size_t value_length;
1817 uint32_t flags;
1818 unsigned int x;
1819 char insert_data[VALUE_SIZE_BUG5];
1820
1821 for (x= 0; x < VALUE_SIZE_BUG5; x++)
1822 insert_data[x]= rand();
1823
1824 memcached_flush(memc, 0);
1825
1826 flags= 245;
1827 rc= memcached_set(memc, keys, key_length,
1828 insert_data, VALUE_SIZE_BUG5,
1829 (time_t)0, flags);
1830 assert(rc == MEMCACHED_SUCCESS);
1831
1832 flags= 0;
1833 value= memcached_get(memc, keys, key_length,
1834 &value_length, &flags, &rc);
1835 assert(flags == 245);
1836 assert(value);
1837 free(value);
1838
1839 rc= memcached_mget(memc, &keys, &key_length, 1);
1840
1841 flags= 0;
1842 value= memcached_fetch(memc, return_key, &return_key_length,
1843 &value_length, &flags, &rc);
1844 assert(flags == 245);
1845 assert(value);
1846 free(value);
1847
1848
1849 return 0;
1850 }
1851
1852 static test_return user_supplied_bug9(memcached_st *memc)
1853 {
1854 memcached_return rc;
1855 char *keys[]= {"UDATA:edevil@sapo.pt", "fudge&*@#", "for^#@&$not"};
1856 size_t key_length[3];
1857 unsigned int x;
1858 uint32_t flags;
1859 unsigned count= 0;
1860
1861 char return_key[MEMCACHED_MAX_KEY];
1862 size_t return_key_length;
1863 char *return_value;
1864 size_t return_value_length;
1865
1866
1867 key_length[0]= strlen("UDATA:edevil@sapo.pt");
1868 key_length[1]= strlen("fudge&*@#");
1869 key_length[2]= strlen("for^#@&$not");
1870
1871
1872 for (x= 0; x < 3; x++)
1873 {
1874 rc= memcached_set(memc, keys[x], key_length[x],
1875 keys[x], key_length[x],
1876 (time_t)50, (uint32_t)9);
1877 assert(rc == MEMCACHED_SUCCESS);
1878 }
1879
1880 rc= memcached_mget(memc, keys, key_length, 3);
1881 assert(rc == MEMCACHED_SUCCESS);
1882
1883 /* We need to empty the server before continueing test */
1884 while ((return_value= memcached_fetch(memc, return_key, &return_key_length,
1885 &return_value_length, &flags, &rc)) != NULL)
1886 {
1887 assert(return_value);
1888 free(return_value);
1889 count++;
1890 }
1891 assert(count == 3);
1892
1893 return 0;
1894 }
1895
1896 /* We are testing with aggressive timeout to get failures */
1897 static test_return user_supplied_bug10(memcached_st *memc)
1898 {
1899 char *key= "foo";
1900 char *value;
1901 size_t value_length= 512;
1902 unsigned int x;
1903 int key_len= 3;
1904 memcached_return rc;
1905 unsigned int set= 1;
1906 memcached_st *mclone= memcached_clone(NULL, memc);
1907 int32_t timeout;
1908
1909 memcached_behavior_set(mclone, MEMCACHED_BEHAVIOR_NO_BLOCK, set);
1910 memcached_behavior_set(mclone, MEMCACHED_BEHAVIOR_TCP_NODELAY, set);
1911 timeout= 2;
1912 memcached_behavior_set(mclone, MEMCACHED_BEHAVIOR_POLL_TIMEOUT, timeout);
1913
1914 value = (char*)malloc(value_length * sizeof(char));
1915
1916 for (x= 0; x < value_length; x++)
1917 value[x]= (char) (x % 127);
1918
1919 for (x= 1; x <= 100000; ++x)
1920 {
1921 rc= memcached_set(mclone, key, key_len,value, value_length, 0, 0);
1922
1923 assert(rc == MEMCACHED_SUCCESS || rc == MEMCACHED_WRITE_FAILURE || rc == MEMCACHED_BUFFERED);
1924
1925 if (rc == MEMCACHED_WRITE_FAILURE)
1926 x--;
1927 }
1928
1929 free(value);
1930 memcached_free(mclone);
1931
1932 return 0;
1933 }
1934
1935 /*
1936 We are looking failures in the async protocol
1937 */
1938 static test_return user_supplied_bug11(memcached_st *memc)
1939 {
1940 char *key= "foo";
1941 char *value;
1942 size_t value_length= 512;
1943 unsigned int x;
1944 int key_len= 3;
1945 memcached_return rc;
1946 unsigned int set= 1;
1947 int32_t timeout;
1948 memcached_st *mclone= memcached_clone(NULL, memc);
1949
1950 memcached_behavior_set(mclone, MEMCACHED_BEHAVIOR_NO_BLOCK, set);
1951 memcached_behavior_set(mclone, MEMCACHED_BEHAVIOR_TCP_NODELAY, set);
1952 timeout= -1;
1953 memcached_behavior_set(mclone, MEMCACHED_BEHAVIOR_POLL_TIMEOUT, timeout);
1954
1955 timeout= (int32_t)memcached_behavior_get(mclone, MEMCACHED_BEHAVIOR_POLL_TIMEOUT);
1956
1957 assert(timeout == -1);
1958
1959 value = (char*)malloc(value_length * sizeof(char));
1960
1961 for (x= 0; x < value_length; x++)
1962 value[x]= (char) (x % 127);
1963
1964 for (x= 1; x <= 100000; ++x)
1965 {
1966 rc= memcached_set(mclone, key, key_len,value, value_length, 0, 0);
1967 }
1968
1969 free(value);
1970 memcached_free(mclone);
1971
1972 return 0;
1973 }
1974
1975 /*
1976 Bug found where incr was not returning MEMCACHED_NOTFOUND when object did not exist.
1977 */
1978 static test_return user_supplied_bug12(memcached_st *memc)
1979 {
1980 memcached_return rc;
1981 uint32_t flags;
1982 size_t value_length;
1983 char *value;
1984 uint64_t number_value;
1985
1986 value= memcached_get(memc, "autoincrement", strlen("autoincrement"),
1987 &value_length, &flags, &rc);
1988 assert(value == NULL);
1989 assert(rc == MEMCACHED_NOTFOUND);
1990
1991 rc= memcached_increment(memc, "autoincrement", strlen("autoincrement"),
1992 1, &number_value);
1993
1994 assert(value == NULL);
1995 /* The binary protocol will set the key if it doesn't exist */
1996 if (memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_BINARY_PROTOCOL) == 1)
1997 assert(rc == MEMCACHED_SUCCESS);
1998 else
1999 assert(rc == MEMCACHED_NOTFOUND);
2000
2001 rc= memcached_set(memc, "autoincrement", strlen("autoincrement"), "1", 1, 0, 0);
2002
2003 value= memcached_get(memc, "autoincrement", strlen("autoincrement"),
2004 &value_length, &flags, &rc);
2005 assert(value);
2006 assert(rc == MEMCACHED_SUCCESS);
2007 free(value);
2008
2009 rc= memcached_increment(memc, "autoincrement", strlen("autoincrement"),
2010 1, &number_value);
2011 assert(number_value == 2);
2012 assert(rc == MEMCACHED_SUCCESS);
2013
2014 return 0;
2015 }
2016
2017 /*
2018 Bug found where command total one more than MEMCACHED_MAX_BUFFER
2019 set key34567890 0 0 8169 \r\n is sent followed by buffer of size 8169, followed by 8169
2020 */
2021 static test_return user_supplied_bug13(memcached_st *memc)
2022 {
2023 char key[] = "key34567890";
2024 char *overflow;
2025 memcached_return rc;
2026 size_t overflowSize;
2027
2028 char commandFirst[]= "set key34567890 0 0 ";
2029 char commandLast[] = " \r\n"; /* first line of command sent to server */
2030 size_t commandLength;
2031 size_t testSize;
2032
2033 commandLength = strlen(commandFirst) + strlen(commandLast) + 4; /* 4 is number of characters in size, probably 8196 */
2034
2035 overflowSize = MEMCACHED_MAX_BUFFER - commandLength;
2036
2037 for (testSize= overflowSize - 1; testSize < overflowSize + 1; testSize++)
2038 {
2039 overflow= malloc(testSize);
2040 assert(overflow != NULL);
2041
2042 memset(overflow, 'x', testSize);
2043 rc= memcached_set(memc, key, strlen(key),
2044 overflow, testSize, 0, 0);
2045 assert(rc == MEMCACHED_SUCCESS);
2046 free(overflow);
2047 }
2048
2049 return 0;
2050 }
2051
2052
2053 /*
2054 Test values of many different sizes
2055 Bug found where command total one more than MEMCACHED_MAX_BUFFER
2056 set key34567890 0 0 8169 \r\n
2057 is sent followed by buffer of size 8169, followed by 8169
2058 */
2059 static test_return user_supplied_bug14(memcached_st *memc)
2060 {
2061 int setter= 1;
2062 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_TCP_NODELAY, setter);
2063 memcached_return rc;
2064 char *key= "foo";
2065 char *value;
2066 size_t value_length= 18000;
2067 char *string;
2068 size_t string_length;
2069 uint32_t flags;
2070 unsigned int x;
2071 size_t current_length;
2072
2073 value = (char*)malloc(value_length);
2074 assert(value);
2075
2076 for (x= 0; x < value_length; x++)
2077 value[x] = (char) (x % 127);
2078
2079 for (current_length= 0; current_length < value_length; current_length++)
2080 {
2081 rc= memcached_set(memc, key, strlen(key),
2082 value, current_length,
2083 (time_t)0, (uint32_t)0);
2084 assert(rc == MEMCACHED_SUCCESS || rc == MEMCACHED_BUFFERED);
2085
2086 string= memcached_get(memc, key, strlen(key),
2087 &string_length, &flags, &rc);
2088
2089 assert(rc == MEMCACHED_SUCCESS);
2090 assert(string_length == current_length);
2091 assert(!memcmp(string, value, string_length));
2092
2093 free(string);
2094 }
2095
2096 free(value);
2097
2098 return 0;
2099 }
2100
2101 /*
2102 Look for zero length value problems
2103 */
2104 static test_return user_supplied_bug15(memcached_st *memc)
2105 {
2106 uint32_t x;
2107 memcached_return rc;
2108 char *key= "mykey";
2109 char *value;
2110 size_t length;
2111 uint32_t flags;
2112
2113 for (x= 0; x < 2; x++)
2114 {
2115 rc= memcached_set(memc, key, strlen(key),
2116 NULL, 0,
2117 (time_t)0, (uint32_t)0);
2118
2119 assert(rc == MEMCACHED_SUCCESS);
2120
2121 value= memcached_get(memc, key, strlen(key),
2122 &length, &flags, &rc);
2123
2124 assert(rc == MEMCACHED_SUCCESS);
2125 assert(value == NULL);
2126 assert(length == 0);
2127 assert(flags == 0);
2128
2129 value= memcached_get(memc, key, strlen(key),
2130 &length, &flags, &rc);
2131
2132 assert(rc == MEMCACHED_SUCCESS);
2133 assert(value == NULL);
2134 assert(length == 0);
2135 assert(flags == 0);
2136 }
2137
2138 return 0;
2139 }
2140
2141 /* Check the return sizes on FLAGS to make sure it stores 32bit unsigned values correctly */
2142 static test_return user_supplied_bug16(memcached_st *memc)
2143 {
2144 memcached_return rc;
2145 char *key= "mykey";
2146 char *value;
2147 size_t length;
2148 uint32_t flags;
2149
2150 rc= memcached_set(memc, key, strlen(key),
2151 NULL, 0,
2152 (time_t)0, UINT32_MAX);
2153
2154 assert(rc == MEMCACHED_SUCCESS);
2155
2156 value= memcached_get(memc, key, strlen(key),
2157 &length, &flags, &rc);
2158
2159 assert(rc == MEMCACHED_SUCCESS);
2160 assert(value == NULL);
2161 assert(length == 0);
2162 assert(flags == UINT32_MAX);
2163
2164 return 0;
2165 }
2166
2167 /* Check the validity of chinese key*/
2168 static test_return user_supplied_bug17(memcached_st *memc)
2169 {
2170 memcached_return rc;
2171 char *key= "豆瓣";
2172 char *value="我们在炎热抑郁的夏天无法停止豆瓣";
2173 char *value2;
2174 size_t length;
2175 uint32_t flags;
2176
2177 rc= memcached_set(memc, key, strlen(key),
2178 value, strlen(value),
2179 (time_t)0, 0);
2180
2181 assert(rc == MEMCACHED_SUCCESS);
2182
2183 value2= memcached_get(memc, key, strlen(key),
2184 &length, &flags, &rc);
2185
2186 assert(length==strlen(value));
2187 assert(rc == MEMCACHED_SUCCESS);
2188 assert(memcmp(value, value2, length)==0);
2189 free(value2);
2190
2191 return 0;
2192 }
2193
2194 /*
2195 From Andrei on IRC
2196 */
2197
2198 test_return user_supplied_bug19(memcached_st *memc)
2199 {
2200 memcached_st *m;
2201 memcached_server_st *s;
2202 memcached_return res;
2203
2204 (void)memc;
2205
2206 m= memcached_create(NULL);
2207 memcached_server_add_with_weight(m, "localhost", 11311, 100);
2208 memcached_server_add_with_weight(m, "localhost", 11312, 100);
2209
2210 s= memcached_server_by_key(m, "a", 1, &res);
2211 memcached_server_free(s);
2212
2213 memcached_free(m);
2214
2215 return 0;
2216 }
2217
2218 /* CAS test from Andei */
2219 test_return user_supplied_bug20(memcached_st *memc)
2220 {
2221 memcached_return status;
2222 memcached_result_st *result, result_obj;
2223 char *key = "abc";
2224 size_t key_len = strlen("abc");
2225 char *value = "foobar";
2226 size_t value_len = strlen(value);
2227
2228 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_SUPPORT_CAS, 1);
2229
2230 status = memcached_set(memc, key, key_len, value, value_len, (time_t)0, (uint32_t)0);
2231 assert(status == MEMCACHED_SUCCESS);
2232
2233 status = memcached_mget(memc, &key, &key_len, 1);
2234 assert(status == MEMCACHED_SUCCESS);
2235
2236 result= memcached_result_create(memc, &result_obj);
2237 assert(result);
2238
2239 memcached_result_create(memc, &result_obj);
2240 result= memcached_fetch_result(memc, &result_obj, &status);
2241
2242 assert(result);
2243 assert(status == MEMCACHED_SUCCESS);
2244
2245 memcached_result_free(result);
2246
2247 return 0;
2248 }
2249
2250 #include "ketama_test_cases.h"
2251 test_return user_supplied_bug18(memcached_st *trash)
2252 {
2253 memcached_return rc;
2254 int value;
2255 int x;
2256 memcached_server_st *server_pool;
2257 memcached_st *memc;
2258
2259 (void)trash;
2260
2261 memc= memcached_create(NULL);
2262 assert(memc);
2263
2264 rc= memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_KETAMA_WEIGHTED, 1);
2265 assert(rc == MEMCACHED_SUCCESS);
2266
2267 value= memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_KETAMA_WEIGHTED);
2268 assert(value == 1);
2269
2270 rc= memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_KETAMA_HASH, MEMCACHED_HASH_MD5);
2271 assert(rc == MEMCACHED_SUCCESS);
2272
2273 value= memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_KETAMA_HASH);
2274 assert(value == MEMCACHED_HASH_MD5);
2275
2276 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");
2277 memcached_server_push(memc, server_pool);
2278
2279 /* verify that the server list was parsed okay. */
2280 assert(memc->number_of_hosts == 8);
2281 assert(strcmp(server_pool[0].hostname, "10.0.1.1") == 0);
2282 assert(server_pool[0].port == 11211);
2283 assert(server_pool[0].weight == 600);
2284 assert(strcmp(server_pool[2].hostname, "10.0.1.3") == 0);
2285 assert(server_pool[2].port == 11211);
2286 assert(server_pool[2].weight == 200);
2287 assert(strcmp(server_pool[7].hostname, "10.0.1.8") == 0);
2288 assert(server_pool[7].port == 11211);
2289 assert(server_pool[7].weight == 100);
2290
2291 /* VDEAAAAA hashes to fffcd1b5, after the last continuum point, and lets
2292 * us test the boundary wraparound.
2293 */
2294 assert(memcached_generate_hash(memc, (char *)"VDEAAAAA", 8) == memc->continuum[0].index);
2295
2296 /* verify the standard ketama set. */
2297 for (x= 0; x < 99; x++)
2298 {
2299 uint32_t server_idx = memcached_generate_hash(memc, test_cases[x].key, strlen(test_cases[x].key));
2300 char *hostname = memc->hosts[server_idx].hostname;
2301 assert(strcmp(hostname, test_cases[x].server) == 0);
2302 }
2303
2304 memcached_server_list_free(server_pool);
2305 memcached_free(memc);
2306
2307 return 0;
2308 }
2309
2310 static test_return result_static(memcached_st *memc)
2311 {
2312 memcached_result_st result;
2313 memcached_result_st *result_ptr;
2314
2315 result_ptr= memcached_result_create(memc, &result);
2316 assert(result.is_allocated == false);
2317 assert(result_ptr);
2318 memcached_result_free(&result);
2319
2320 return 0;
2321 }
2322
2323 static test_return result_alloc(memcached_st *memc)
2324 {
2325 memcached_result_st *result;
2326
2327 result= memcached_result_create(memc, NULL);
2328 assert(result);
2329 memcached_result_free(result);
2330
2331 return 0;
2332 }
2333
2334 static test_return string_static_null(memcached_st *memc)
2335 {
2336 memcached_string_st string;
2337 memcached_string_st *string_ptr;
2338
2339 string_ptr= memcached_string_create(memc, &string, 0);
2340 assert(string.is_allocated == false);
2341 assert(string_ptr);
2342 memcached_string_free(&string);
2343
2344 return 0;
2345 }
2346
2347 static test_return string_alloc_null(memcached_st *memc)
2348 {
2349 memcached_string_st *string;
2350
2351 string= memcached_string_create(memc, NULL, 0);
2352 assert(string);
2353 memcached_string_free(string);
2354
2355 return 0;
2356 }
2357
2358 static test_return string_alloc_with_size(memcached_st *memc)
2359 {
2360 memcached_string_st *string;
2361
2362 string= memcached_string_create(memc, NULL, 1024);
2363 assert(string);
2364 memcached_string_free(string);
2365
2366 return 0;
2367 }
2368
2369 static test_return string_alloc_with_size_toobig(memcached_st *memc)
2370 {
2371 memcached_string_st *string;
2372
2373 string= memcached_string_create(memc, NULL, INT64_MAX);
2374 assert(string == NULL);
2375
2376 return 0;
2377 }
2378
2379 static test_return string_alloc_append(memcached_st *memc)
2380 {
2381 unsigned int x;
2382 char buffer[SMALL_STRING_LEN];
2383 memcached_string_st *string;
2384
2385 /* Ring the bell! */
2386 memset(buffer, 6, SMALL_STRING_LEN);
2387
2388 string= memcached_string_create(memc, NULL, 100);
2389 assert(string);
2390
2391 for (x= 0; x < 1024; x++)
2392 {
2393 memcached_return rc;
2394 rc= memcached_string_append(string, buffer, SMALL_STRING_LEN);
2395 assert(rc == MEMCACHED_SUCCESS);
2396 }
2397 memcached_string_free(string);
2398
2399 return 0;
2400 }
2401
2402 static test_return string_alloc_append_toobig(memcached_st *memc)
2403 {
2404 memcached_return rc;
2405 unsigned int x;
2406 char buffer[SMALL_STRING_LEN];
2407 memcached_string_st *string;
2408
2409 /* Ring the bell! */
2410 memset(buffer, 6, SMALL_STRING_LEN);
2411
2412 string= memcached_string_create(memc, NULL, 100);
2413 assert(string);
2414
2415 for (x= 0; x < 1024; x++)
2416 {
2417 rc= memcached_string_append(string, buffer, SMALL_STRING_LEN);
2418 assert(rc == MEMCACHED_SUCCESS);
2419 }
2420 rc= memcached_string_append(string, buffer, INT64_MAX);
2421 assert(rc == MEMCACHED_MEMORY_ALLOCATION_FAILURE);
2422 memcached_string_free(string);
2423
2424 return 0;
2425 }
2426
2427 static test_return cleanup_pairs(memcached_st *memc __attribute__((unused)))
2428 {
2429 pairs_free(global_pairs);
2430
2431 return 0;
2432 }
2433
2434 static test_return generate_pairs(memcached_st *memc __attribute__((unused)))
2435 {
2436 unsigned long long x;
2437 global_pairs= pairs_generate(GLOBAL_COUNT, 400);
2438 global_count= GLOBAL_COUNT;
2439
2440 for (x= 0; x < global_count; x++)
2441 {
2442 global_keys[x]= global_pairs[x].key;
2443 global_keys_length[x]= global_pairs[x].key_length;
2444 }
2445
2446 return 0;
2447 }
2448
2449 static test_return generate_large_pairs(memcached_st *memc __attribute__((unused)))
2450 {
2451 unsigned long long x;
2452 global_pairs= pairs_generate(GLOBAL2_COUNT, MEMCACHED_MAX_BUFFER+10);
2453 global_count= GLOBAL2_COUNT;
2454
2455 for (x= 0; x < global_count; x++)
2456 {
2457 global_keys[x]= global_pairs[x].key;
2458 global_keys_length[x]= global_pairs[x].key_length;
2459 }
2460
2461 return 0;
2462 }
2463
2464 static test_return generate_data(memcached_st *memc)
2465 {
2466 execute_set(memc, global_pairs, global_count);
2467
2468 return 0;
2469 }
2470
2471 static test_return generate_data_with_stats(memcached_st *memc)
2472 {
2473 memcached_stat_st *stat_p;
2474 memcached_return rc;
2475 uint32_t host_index= 0;
2476 execute_set(memc, global_pairs, global_count);
2477
2478 //TODO: hosts used size stats
2479 stat_p= memcached_stat(memc, NULL, &rc);
2480 assert(stat_p);
2481
2482 for (host_index= 0; host_index < SERVERS_TO_CREATE; host_index++)
2483 {
2484 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);
2485 }
2486
2487 memcached_stat_free(NULL, stat_p);
2488
2489 return 0;
2490 }
2491 static test_return generate_buffer_data(memcached_st *memc)
2492 {
2493 int latch= 0;
2494
2495 latch= 1;
2496 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_BUFFER_REQUESTS, latch);
2497 generate_data(memc);
2498
2499 return 0;
2500 }
2501
2502 static test_return get_read_count(memcached_st *memc)
2503 {
2504 unsigned int x;
2505 memcached_return rc;
2506 memcached_st *clone;
2507
2508 clone= memcached_clone(NULL, memc);
2509 assert(clone);
2510
2511 memcached_server_add_with_weight(clone, "localhost", 6666, 0);
2512
2513 {
2514 char *return_value;
2515 size_t return_value_length;
2516 uint32_t flags;
2517 uint32_t count;
2518
2519 for (x= count= 0; x < global_count; x++)
2520 {
2521 return_value= memcached_get(clone, global_keys[x], global_keys_length[x],
2522 &return_value_length, &flags, &rc);
2523 if (rc == MEMCACHED_SUCCESS)
2524 {
2525 count++;
2526 if (return_value)
2527 free(return_value);
2528 }
2529 }
2530 fprintf(stderr, "\t%u -> %u", global_count, count);
2531 }
2532
2533 memcached_free(clone);
2534
2535 return 0;
2536 }
2537
2538 static test_return get_read(memcached_st *memc)
2539 {
2540 unsigned int x;
2541 memcached_return rc;
2542
2543 {
2544 char *return_value;
2545 size_t return_value_length;
2546 uint32_t flags;
2547
2548 for (x= 0; x < global_count; x++)
2549 {
2550 return_value= memcached_get(memc, global_keys[x], global_keys_length[x],
2551 &return_value_length, &flags, &rc);
2552 /*
2553 assert(return_value);
2554 assert(rc == MEMCACHED_SUCCESS);
2555 */
2556 if (rc == MEMCACHED_SUCCESS && return_value)
2557 free(return_value);
2558 }
2559 }
2560
2561 return 0;
2562 }
2563
2564 static test_return mget_read(memcached_st *memc)
2565 {
2566 memcached_return rc;
2567
2568 rc= memcached_mget(memc, global_keys, global_keys_length, global_count);
2569 assert(rc == MEMCACHED_SUCCESS);
2570 /* Turn this into a help function */
2571 {
2572 char return_key[MEMCACHED_MAX_KEY];
2573 size_t return_key_length;
2574 char *return_value;
2575 size_t return_value_length;
2576 uint32_t flags;
2577
2578 while ((return_value= memcached_fetch(memc, return_key, &return_key_length,
2579 &return_value_length, &flags, &rc)))
2580 {
2581 assert(return_value);
2582 assert(rc == MEMCACHED_SUCCESS);
2583 free(return_value);
2584 }
2585 }
2586
2587 return 0;
2588 }
2589
2590 static test_return mget_read_result(memcached_st *memc)
2591 {
2592 memcached_return rc;
2593
2594 rc= memcached_mget(memc, global_keys, global_keys_length, global_count);
2595 assert(rc == MEMCACHED_SUCCESS);
2596 /* Turn this into a help function */
2597 {
2598 memcached_result_st results_obj;
2599 memcached_result_st *results;
2600
2601 results= memcached_result_create(memc, &results_obj);
2602
2603 while ((results= memcached_fetch_result(memc, &results_obj, &rc)))
2604 {
2605 assert(results);
2606 assert(rc == MEMCACHED_SUCCESS);
2607 }
2608
2609 memcached_result_free(&results_obj);
2610 }
2611
2612 return 0;
2613 }
2614
2615 static test_return mget_read_function(memcached_st *memc)
2616 {
2617 memcached_return rc;
2618 unsigned int counter;
2619 memcached_execute_function callbacks[1];
2620
2621 rc= memcached_mget(memc, global_keys, global_keys_length, global_count);
2622 assert(rc == MEMCACHED_SUCCESS);
2623
2624 callbacks[0]= &callback_counter;
2625 counter= 0;
2626 rc= memcached_fetch_execute(memc, callbacks, (void *)&counter, 1);
2627
2628 return 0;
2629 }
2630
2631 static test_return delete_generate(memcached_st *memc)
2632 {
2633 unsigned int x;
2634
2635 for (x= 0; x < global_count; x++)
2636 {
2637 (void)memcached_delete(memc, global_keys[x], global_keys_length[x], (time_t)0);
2638 }
2639
2640 return 0;
2641 }
2642
2643 static test_return delete_buffer_generate(memcached_st *memc)
2644 {
2645 int latch= 0;
2646 unsigned int x;
2647
2648 latch= 1;
2649 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_BUFFER_REQUESTS, latch);
2650
2651 for (x= 0; x < global_count; x++)
2652 {
2653 (void)memcached_delete(memc, global_keys[x], global_keys_length[x], (time_t)0);
2654 }
2655
2656 return 0;
2657 }
2658
2659 static test_return free_data(memcached_st *memc __attribute__((unused)))
2660 {
2661 pairs_free(global_pairs);
2662
2663 return 0;
2664 }
2665
2666 static test_return add_host_test1(memcached_st *memc)
2667 {
2668 unsigned int x;
2669 memcached_return rc;
2670 char servername[]= "0.example.com";
2671 memcached_server_st *servers;
2672
2673 servers= memcached_server_list_append_with_weight(NULL, servername, 400, 0, &rc);
2674 assert(servers);
2675 assert(1 == memcached_server_list_count(servers));
2676
2677 for (x= 2; x < 20; x++)
2678 {
2679 char buffer[SMALL_STRING_LEN];
2680
2681 snprintf(buffer, SMALL_STRING_LEN, "%u.example.com", 400+x);
2682 servers= memcached_server_list_append_with_weight(servers, buffer, 401, 0,
2683 &rc);
2684 assert(rc == MEMCACHED_SUCCESS);
2685 assert(x == memcached_server_list_count(servers));
2686 }
2687
2688 rc= memcached_server_push(memc, servers);
2689 assert(rc == MEMCACHED_SUCCESS);
2690 rc= memcached_server_push(memc, servers);
2691 assert(rc == MEMCACHED_SUCCESS);
2692
2693 memcached_server_list_free(servers);
2694
2695 return 0;
2696 }
2697
2698 static memcached_return pre_nonblock(memcached_st *memc)
2699 {
2700 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_NO_BLOCK, 0);
2701
2702 return MEMCACHED_SUCCESS;
2703 }
2704
2705 static memcached_return pre_nonblock_binary(memcached_st *memc)
2706 {
2707 memcached_return rc= MEMCACHED_FAILURE;
2708 memcached_st *clone;
2709
2710 clone= memcached_clone(NULL, memc);
2711 assert(clone);
2712 // The memcached_version needs to be done on a clone, because the server
2713 // will not toggle protocol on an connection.
2714 memcached_version(clone);
2715
2716 if (clone->hosts[0].major_version >= 1 && clone->hosts[0].minor_version > 2)
2717 {
2718 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_NO_BLOCK, 0);
2719 rc = memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_BINARY_PROTOCOL, 1);
2720 assert(rc == MEMCACHED_SUCCESS);
2721 assert(memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_BINARY_PROTOCOL) == 1);
2722 }
2723
2724 memcached_free(clone);
2725 return rc;
2726 }
2727
2728 static memcached_return pre_murmur(memcached_st *memc)
2729 {
2730 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_HASH, (uint64_t)MEMCACHED_HASH_MURMUR);
2731
2732 return MEMCACHED_SUCCESS;
2733 }
2734
2735 static memcached_return pre_jenkins(memcached_st *memc)
2736 {
2737 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_HASH, (uint64_t)MEMCACHED_HASH_JENKINS);
2738
2739 return MEMCACHED_SUCCESS;
2740 }
2741
2742
2743 static memcached_return pre_md5(memcached_st *memc)
2744 {
2745 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_HASH, (uint64_t)MEMCACHED_HASH_MD5);
2746
2747 return MEMCACHED_SUCCESS;
2748 }
2749
2750 static memcached_return pre_crc(memcached_st *memc)
2751 {
2752 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_HASH, (uint64_t)MEMCACHED_HASH_CRC);
2753
2754 return MEMCACHED_SUCCESS;
2755 }
2756
2757 static memcached_return pre_hsieh(memcached_st *memc)
2758 {
2759 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_HASH, (uint64_t)MEMCACHED_HASH_HSIEH);
2760
2761 return MEMCACHED_SUCCESS;
2762 }
2763
2764 static memcached_return pre_hash_fnv1_64(memcached_st *memc)
2765 {
2766 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_HASH, (uint64_t)MEMCACHED_HASH_FNV1_64);
2767
2768 return MEMCACHED_SUCCESS;
2769 }
2770
2771 static memcached_return pre_hash_fnv1a_64(memcached_st *memc)
2772 {
2773 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_HASH, (uint64_t)MEMCACHED_HASH_FNV1A_64);
2774
2775 return MEMCACHED_SUCCESS;
2776 }
2777
2778 static memcached_return pre_hash_fnv1_32(memcached_st *memc)
2779 {
2780 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_HASH, (uint64_t)MEMCACHED_HASH_FNV1_32);
2781
2782 return MEMCACHED_SUCCESS;
2783 }
2784
2785 static memcached_return pre_hash_fnv1a_32(memcached_st *memc)
2786 {
2787 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_HASH, (uint64_t)MEMCACHED_HASH_FNV1A_32);
2788
2789 return MEMCACHED_SUCCESS;
2790 }
2791
2792 static memcached_return pre_behavior_ketama(memcached_st *memc)
2793 {
2794 memcached_return rc;
2795 uint64_t value;
2796
2797 rc= memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_KETAMA, 1);
2798 assert(rc == MEMCACHED_SUCCESS);
2799
2800 value= memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_KETAMA);
2801 assert(value == 1);
2802
2803 return MEMCACHED_SUCCESS;
2804 }
2805
2806 static memcached_return pre_behavior_ketama_weighted(memcached_st *memc)
2807 {
2808 memcached_return rc;
2809 uint64_t value;
2810
2811 rc= memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_KETAMA_WEIGHTED, 1);
2812 assert(rc == MEMCACHED_SUCCESS);
2813
2814 value= memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_KETAMA_WEIGHTED);
2815 assert(value == 1);
2816
2817 rc= memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_KETAMA_HASH, MEMCACHED_HASH_MD5);
2818 assert(rc == MEMCACHED_SUCCESS);
2819
2820 value= memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_KETAMA_HASH);
2821 assert(value == MEMCACHED_HASH_MD5);
2822 return MEMCACHED_SUCCESS;
2823 }
2824
2825 static memcached_return pre_binary(memcached_st *memc)
2826 {
2827 memcached_return rc= MEMCACHED_FAILURE;
2828 memcached_st *clone;
2829
2830 clone= memcached_clone(NULL, memc);
2831 assert(clone);
2832 // The memcached_version needs to be done on a clone, because the server
2833 // will not toggle protocol on an connection.
2834 memcached_version(clone);
2835
2836 if (clone->hosts[0].major_version >= 1 && clone->hosts[0].minor_version > 2)
2837 {
2838 rc = memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_BINARY_PROTOCOL, 1);
2839 assert(rc == MEMCACHED_SUCCESS);
2840 assert(memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_BINARY_PROTOCOL) == 1);
2841 }
2842
2843 memcached_free(clone);
2844 return rc;
2845 }
2846
2847 static void my_free(memcached_st *ptr __attribute__((unused)), void *mem)
2848 {
2849 free(mem);
2850 }
2851
2852 static void *my_malloc(memcached_st *ptr __attribute__((unused)), const size_t size)
2853 {
2854 return malloc(size);
2855 }
2856
2857 static void *my_realloc(memcached_st *ptr __attribute__((unused)), void *mem, const size_t size)
2858 {
2859 return realloc(mem, size);
2860 }
2861
2862 static memcached_return set_prefix(memcached_st *memc)
2863 {
2864 memcached_return rc;
2865 const char *key= "mine";
2866 char *value;
2867
2868 /* Make sure be default none exists */
2869 value= memcached_callback_get(memc, MEMCACHED_CALLBACK_PREFIX_KEY, &rc);
2870 assert(rc == MEMCACHED_FAILURE);
2871
2872 /* Test a clean set */
2873 rc= memcached_callback_set(memc, MEMCACHED_CALLBACK_PREFIX_KEY, (void *)key);
2874 assert(rc == MEMCACHED_SUCCESS);
2875
2876 value= memcached_callback_get(memc, MEMCACHED_CALLBACK_PREFIX_KEY, &rc);
2877 assert(memcmp(value, key, 4) == 0);
2878 assert(rc == MEMCACHED_SUCCESS);
2879
2880 /* Test that we can turn it off */
2881 rc= memcached_callback_set(memc, MEMCACHED_CALLBACK_PREFIX_KEY, NULL);
2882 assert(rc == MEMCACHED_SUCCESS);
2883
2884 value= memcached_callback_get(memc, MEMCACHED_CALLBACK_PREFIX_KEY, &rc);
2885 assert(rc == MEMCACHED_FAILURE);
2886
2887 /* Now setup for main test */
2888 rc= memcached_callback_set(memc, MEMCACHED_CALLBACK_PREFIX_KEY, (void *)key);
2889 assert(rc == MEMCACHED_SUCCESS);
2890
2891 value= memcached_callback_get(memc, MEMCACHED_CALLBACK_PREFIX_KEY, &rc);
2892 assert(rc == MEMCACHED_SUCCESS);
2893 assert(memcmp(value, key, 4) == 0);
2894
2895 /* Set to Zero, and then Set to something too large */
2896 {
2897 char *long_key;
2898 rc= memcached_callback_set(memc, MEMCACHED_CALLBACK_PREFIX_KEY, NULL);
2899 assert(rc == MEMCACHED_SUCCESS);
2900
2901 value= memcached_callback_get(memc, MEMCACHED_CALLBACK_PREFIX_KEY, &rc);
2902 assert(rc == MEMCACHED_FAILURE);
2903 assert(value == NULL);
2904
2905 /* Test a long key for failure */
2906 /* TODO, extend test to determine based on setting, what result should be */
2907 long_key= "Thisismorethentheallottednumberofcharacters";
2908 rc= memcached_callback_set(memc, MEMCACHED_CALLBACK_PREFIX_KEY, long_key);
2909 //assert(rc == MEMCACHED_BAD_KEY_PROVIDED);
2910 assert(rc == MEMCACHED_SUCCESS);
2911
2912 /* Now test a key with spaces (which will fail from long key, since bad key is not set) */
2913 long_key= "This is more then the allotted number of characters";
2914 rc= memcached_callback_set(memc, MEMCACHED_CALLBACK_PREFIX_KEY, long_key);
2915 assert(rc == MEMCACHED_BAD_KEY_PROVIDED);
2916
2917 /* Test for a bad prefix, but with a short key */
2918 rc= memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_VERIFY_KEY, 1);
2919 assert(rc == MEMCACHED_SUCCESS);
2920
2921 long_key= "dog cat";
2922 rc= memcached_callback_set(memc, MEMCACHED_CALLBACK_PREFIX_KEY, long_key);
2923 assert(rc == MEMCACHED_BAD_KEY_PROVIDED);
2924 }
2925
2926 return MEMCACHED_SUCCESS;
2927 }
2928
2929 static memcached_return set_memory_alloc(memcached_st *memc)
2930 {
2931 {
2932 memcached_malloc_function test_ptr;
2933 memcached_return rc;
2934
2935 rc= memcached_callback_set(memc, MEMCACHED_CALLBACK_MALLOC_FUNCTION, (void*)&my_malloc);
2936 assert(rc == MEMCACHED_SUCCESS);
2937 test_ptr= (memcached_malloc_function)memcached_callback_get(memc, MEMCACHED_CALLBACK_MALLOC_FUNCTION, &rc);
2938 assert(rc == MEMCACHED_SUCCESS);
2939 assert(test_ptr == my_malloc);
2940 }
2941
2942 {
2943 memcached_realloc_function test_ptr;
2944 memcached_return rc;
2945
2946 rc= memcached_callback_set(memc, MEMCACHED_CALLBACK_REALLOC_FUNCTION, (void*)&my_realloc);
2947 assert(rc == MEMCACHED_SUCCESS);
2948 test_ptr= (memcached_realloc_function)memcached_callback_get(memc, MEMCACHED_CALLBACK_REALLOC_FUNCTION, &rc);
2949 assert(rc == MEMCACHED_SUCCESS);
2950 assert(test_ptr == my_realloc);
2951 }
2952
2953 {
2954 memcached_free_function test_ptr;
2955 memcached_return rc;
2956
2957 rc= memcached_callback_set(memc, MEMCACHED_CALLBACK_FREE_FUNCTION, (void*)my_free);
2958 assert(rc == MEMCACHED_SUCCESS);
2959 test_ptr= (memcached_free_function)memcached_callback_get(memc, MEMCACHED_CALLBACK_FREE_FUNCTION, &rc);
2960 assert(rc == MEMCACHED_SUCCESS);
2961 assert(test_ptr == my_free);
2962 }
2963
2964 return MEMCACHED_SUCCESS;
2965 }
2966
2967 static memcached_return enable_consistent(memcached_st *memc)
2968 {
2969 memcached_server_distribution value= MEMCACHED_DISTRIBUTION_CONSISTENT;
2970 memcached_hash hash;
2971 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_DISTRIBUTION, value);
2972 pre_hsieh(memc);
2973
2974 value= (memcached_server_distribution)memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_DISTRIBUTION);
2975 assert(value == MEMCACHED_DISTRIBUTION_CONSISTENT);
2976
2977 hash= (memcached_hash)memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_HASH);
2978 assert(hash == MEMCACHED_HASH_HSIEH);
2979
2980
2981 return MEMCACHED_SUCCESS;
2982 }
2983
2984 static memcached_return enable_cas(memcached_st *memc)
2985 {
2986 unsigned int set= 1;
2987
2988 memcached_version(memc);
2989
2990 if ((memc->hosts[0].major_version >= 1 && (memc->hosts[0].minor_version == 2 && memc->hosts[0].micro_version >= 4))
2991 || memc->hosts[0].minor_version > 2)
2992 {
2993 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_SUPPORT_CAS, set);
2994
2995 return MEMCACHED_SUCCESS;
2996 }
2997
2998 return MEMCACHED_FAILURE;
2999 }
3000
3001 static memcached_return check_for_1_2_3(memcached_st *memc)
3002 {
3003 memcached_version(memc);
3004
3005 if ((memc->hosts[0].major_version >= 1 && (memc->hosts[0].minor_version == 2 && memc->hosts[0].micro_version >= 4))
3006 || memc->hosts[0].minor_version > 2)
3007 return MEMCACHED_SUCCESS;
3008
3009 return MEMCACHED_FAILURE;
3010 }
3011
3012 static memcached_return pre_unix_socket(memcached_st *memc)
3013 {
3014 memcached_return rc;
3015 struct stat buf;
3016
3017 memcached_server_list_free(memc->hosts);
3018 memc->hosts= NULL;
3019 memc->number_of_hosts= 0;
3020
3021 if (stat("/tmp/memcached.socket", &buf))
3022 return MEMCACHED_FAILURE;
3023
3024 rc= memcached_server_add_unix_socket_with_weight(memc, "/tmp/memcached.socket", 0);
3025
3026 return rc;
3027 }
3028
3029 static memcached_return pre_nodelay(memcached_st *memc)
3030 {
3031 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_NO_BLOCK, 0);
3032 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_TCP_NODELAY, 0);
3033
3034 return MEMCACHED_SUCCESS;
3035 }
3036
3037 static memcached_return pre_settimer(memcached_st *memc)
3038 {
3039 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_SND_TIMEOUT, 1000);
3040 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_RCV_TIMEOUT, 1000);
3041
3042 return MEMCACHED_SUCCESS;
3043 }
3044
3045 static memcached_return poll_timeout(memcached_st *memc)
3046 {
3047 int32_t timeout;
3048
3049 timeout= 100;
3050
3051 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_POLL_TIMEOUT, timeout);
3052
3053 timeout= (int32_t)memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_POLL_TIMEOUT);
3054
3055 assert(timeout == 100);
3056
3057 return MEMCACHED_SUCCESS;
3058 }
3059
3060 static test_return noreply_test(memcached_st *memc)
3061 {
3062 memcached_return ret;
3063 ret= memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_NOREPLY, 1);
3064 assert(ret == MEMCACHED_SUCCESS);
3065 ret= memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_BUFFER_REQUESTS, 1);
3066 assert(ret == MEMCACHED_SUCCESS);
3067 ret= memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_SUPPORT_CAS, 1);
3068 assert(ret == MEMCACHED_SUCCESS);
3069 assert(memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_NOREPLY) == 1);
3070 assert(memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_BUFFER_REQUESTS) == 1);
3071 assert(memcached_behavior_get(memc, MEMCACHED_BEHAVIOR_SUPPORT_CAS) == 1);
3072
3073 for (int count=0; count < 5; ++count)
3074 {
3075 for (int x=0; x < 100; ++x)
3076 {
3077 char key[10];
3078 size_t len=sprintf(key, "%d", x);
3079 switch (count)
3080 {
3081 case 0:
3082 ret=memcached_add(memc, key, len, key, len, 0, 0);
3083 break;
3084 case 1:
3085 ret=memcached_replace(memc, key, len, key, len, 0, 0);
3086 break;
3087 case 2:
3088 ret=memcached_set(memc, key, len, key, len, 0, 0);
3089 break;
3090 case 3:
3091 ret=memcached_append(memc, key, len, key, len, 0, 0);
3092 break;
3093 case 4:
3094 ret=memcached_prepend(memc, key, len, key, len, 0, 0);
3095 break;
3096 }
3097 assert(ret == MEMCACHED_SUCCESS || ret == MEMCACHED_BUFFERED);
3098 }
3099
3100 /*
3101 ** NOTE: Don't ever do this in your code! this is not a supported use of the
3102 ** API and is _ONLY_ done this way to verify that the library works the
3103 ** way it is supposed to do!!!!
3104 */
3105 int no_msg=0;
3106 for (int x=0; x < memc->number_of_hosts; ++x)
3107 no_msg+=memc->hosts[x].cursor_active;
3108
3109 assert(no_msg == 0);
3110 assert(memcached_flush_buffers(memc) == MEMCACHED_SUCCESS);
3111
3112 /*
3113 ** Now validate that all items was set properly!
3114 */
3115 for (int x=0; x < 100; ++x)
3116 {
3117 char key[10];
3118 size_t len=sprintf(key, "%d", x);
3119 size_t length;
3120 uint32_t flags;
3121 char* value=memcached_get(memc, key, strlen(key),
3122 &length, &flags, &ret);
3123 assert(ret == MEMCACHED_SUCCESS && value != NULL);
3124 switch (count)
3125 {
3126 case 0: /* FALLTHROUGH */
3127 case 1: /* FALLTHROUGH */
3128 case 2:
3129 assert(strncmp(value, key, len) == 0);
3130 assert(len == length);
3131 break;
3132 case 3:
3133 assert(length == len * 2);
3134 break;
3135 case 4:
3136 assert(length == len * 3);
3137 break;
3138 }
3139 free(value);
3140 }
3141 }
3142
3143 /* Try setting an illegal cas value (should not return an error to
3144 * the caller (because we don't expect a return message from the server)
3145 */
3146 char* keys[]= {"0"};
3147 size_t lengths[]= {1};
3148 size_t length;
3149 uint32_t flags;
3150 memcached_result_st results_obj;
3151 memcached_result_st *results;
3152 ret=memcached_mget(memc, keys, lengths, 1);
3153 assert(ret == MEMCACHED_SUCCESS);
3154
3155 results=memcached_result_create(memc, &results_obj);
3156 assert(results);
3157 results=memcached_fetch_result(memc, &results_obj, &ret);
3158 assert(results);
3159 assert(ret == MEMCACHED_SUCCESS);
3160 uint64_t cas= memcached_result_cas(results);
3161 memcached_result_free(&results_obj);
3162
3163 ret= memcached_cas(memc, keys[0], lengths[0], keys[0], lengths[0], 0, 0, cas);
3164 assert(ret == MEMCACHED_SUCCESS);
3165
3166 /*
3167 * The item will have a new cas value, so try to set it again with the old
3168 * value. This should fail!
3169 */
3170 ret= memcached_cas(memc, keys[0], lengths[0], keys[0], lengths[0], 0, 0, cas);
3171 assert(ret == MEMCACHED_SUCCESS);
3172 assert(memcached_flush_buffers(memc) == MEMCACHED_SUCCESS);
3173 char* value=memcached_get(memc, keys[0], lengths[0], &length, &flags, &ret);
3174 assert(ret == MEMCACHED_SUCCESS && value != NULL);
3175 free(value);
3176
3177 return TEST_SUCCESS;
3178 }
3179
3180 static test_return analyzer_test(memcached_st *memc)
3181 {
3182 memcached_return rc;
3183 memcached_stat_st *stat;
3184 memcached_analysis_st *report;
3185
3186 stat= memcached_stat(memc, NULL, &rc);
3187 assert(rc == MEMCACHED_SUCCESS);
3188 assert(stat);
3189
3190 report= memcached_analyze(memc, stat, &rc);
3191 assert(rc == MEMCACHED_SUCCESS);
3192 assert(report);
3193
3194 free(report);
3195 memcached_stat_free(NULL, stat);
3196
3197 return TEST_SUCCESS;
3198 }
3199
3200 static void increment_request_id(uint16_t *id)
3201 {
3202 (*id)++;
3203 if ((*id & UDP_REQUEST_ID_THREAD_MASK) != 0)
3204 *id= 0;
3205 }
3206
3207 static uint16_t *get_udp_request_ids(memcached_st *memc)
3208 {
3209 uint16_t *ids= malloc(sizeof(uint16_t) * memc->number_of_hosts);
3210 assert(ids != NULL);
3211 unsigned int x;
3212 for (x= 0; x < memc->number_of_hosts; x++)
3213 ids[x]= get_udp_datagram_request_id((struct udp_datagram_header_st *) memc->hosts[x].write_buffer);
3214
3215 return ids;
3216 }
3217
3218 static test_return post_udp_op_check(memcached_st *memc, uint16_t *expected_req_ids)
3219 {
3220 unsigned int x;
3221 memcached_server_st *cur_server = memc->hosts;
3222 uint16_t *cur_req_ids = get_udp_request_ids(memc);
3223 for (x= 0; x < memc->number_of_hosts; x++)
3224 {
3225 assert(cur_server[x].cursor_active == 0);
3226 assert(cur_req_ids[x] == expected_req_ids[x]);
3227 }
3228 free(expected_req_ids);
3229 free(cur_req_ids);
3230 return TEST_SUCCESS;
3231 }
3232
3233 /*
3234 ** There is a little bit of a hack here, instead of removing
3235 ** the servers, I just set num host to 0 and them add then new udp servers
3236 **/
3237 static memcached_return init_udp(memcached_st *memc)
3238 {
3239 memcached_version(memc);
3240 /* For the time being, only support udp test for >= 1.2.6 && < 1.3 */
3241 if (memc->hosts[0].major_version != 1 || memc->hosts[0].minor_version != 2
3242 || memc->hosts[0].micro_version < 6)
3243 return MEMCACHED_FAILURE;
3244
3245 uint32_t num_hosts= memc->number_of_hosts;
3246 unsigned int x= 0;
3247 memcached_server_st servers[num_hosts];
3248 memcpy(servers, memc->hosts, sizeof(memcached_server_st) * num_hosts);
3249 memc->number_of_hosts= 0;
3250 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_USE_UDP, 1);
3251 for (x= 0; x < num_hosts; x++)
3252 {
3253 assert(memcached_server_add_udp(memc, servers[x].hostname, servers[x].port) == MEMCACHED_SUCCESS);
3254 assert(memc->hosts[x].write_buffer_offset == UDP_DATAGRAM_HEADER_LENGTH);
3255 }
3256 return MEMCACHED_SUCCESS;
3257 }
3258
3259 static memcached_return binary_init_udp(memcached_st *memc)
3260 {
3261 pre_binary(memc);
3262 return init_udp(memc);
3263 }
3264
3265 /* Make sure that I cant add a tcp server to a udp client */
3266 static test_return add_tcp_server_udp_client_test(memcached_st *memc)
3267 {
3268 memcached_server_st server;
3269 memcached_server_clone(&server, &memc->hosts[0]);
3270 assert(memcached_server_remove(&(memc->hosts[0])) == MEMCACHED_SUCCESS);
3271 assert(memcached_server_add(memc, server.hostname, server.port) == MEMCACHED_INVALID_HOST_PROTOCOL);
3272 return TEST_SUCCESS;
3273 }
3274
3275 /* Make sure that I cant add a udp server to a tcp client */
3276 static test_return add_udp_server_tcp_client_test(memcached_st *memc)
3277 {
3278 memcached_server_st server;
3279 memcached_server_clone(&server, &memc->hosts[0]);
3280 assert(memcached_server_remove(&(memc->hosts[0])) == MEMCACHED_SUCCESS);
3281
3282 memcached_st tcp_client;
3283 memcached_create(&tcp_client);
3284 assert(memcached_server_add_udp(&tcp_client, server.hostname, server.port) == MEMCACHED_INVALID_HOST_PROTOCOL);
3285 return TEST_SUCCESS;
3286 }
3287
3288 static test_return set_udp_behavior_test(memcached_st *memc)
3289 {
3290
3291 memcached_quit(memc);
3292 memc->number_of_hosts= 0;
3293 run_distribution(memc);
3294 assert(memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_USE_UDP, 1) == MEMCACHED_SUCCESS);
3295 assert(memc->flags & MEM_USE_UDP);
3296 assert(memc->flags & MEM_NOREPLY);;
3297
3298 assert(memc->number_of_hosts == 0);
3299
3300 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_USE_UDP,0);
3301 assert(!(memc->flags & MEM_USE_UDP));
3302 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_NOREPLY,0);
3303 assert(!(memc->flags & MEM_NOREPLY));
3304 return TEST_SUCCESS;
3305 }
3306
3307 static test_return udp_set_test(memcached_st *memc)
3308 {
3309 unsigned int x= 0;
3310 unsigned int num_iters= 1025; //request id rolls over at 1024
3311 for (x= 0; x < num_iters;x++)
3312 {
3313 memcached_return rc;
3314 char *key= "foo";
3315 char *value= "when we sanitize";
3316 uint16_t *expected_ids= get_udp_request_ids(memc);
3317 unsigned int server_key= memcached_generate_hash(memc,key,strlen(key));
3318 size_t init_offset= memc->hosts[server_key].write_buffer_offset;
3319 rc= memcached_set(memc, key, strlen(key),
3320 value, strlen(value),
3321 (time_t)0, (uint32_t)0);
3322 assert(rc == MEMCACHED_SUCCESS || rc == MEMCACHED_BUFFERED);
3323 /** NB, the check below assumes that if new write_ptr is less than
3324 * the original write_ptr that we have flushed. For large payloads, this
3325 * maybe an invalid assumption, but for the small payload we have it is OK
3326 */
3327 if (rc == MEMCACHED_SUCCESS ||
3328 memc->hosts[server_key].write_buffer_offset < init_offset)
3329 increment_request_id(&expected_ids[server_key]);
3330
3331 if (rc == MEMCACHED_SUCCESS)
3332 {
3333 assert(memc->hosts[server_key].write_buffer_offset == UDP_DATAGRAM_HEADER_LENGTH);
3334 }
3335 else
3336 {
3337 assert(memc->hosts[server_key].write_buffer_offset != UDP_DATAGRAM_HEADER_LENGTH);
3338 assert(memc->hosts[server_key].write_buffer_offset <= MAX_UDP_DATAGRAM_LENGTH);
3339 }
3340 assert(post_udp_op_check(memc,expected_ids) == TEST_SUCCESS);
3341 }
3342 return TEST_SUCCESS;
3343 }
3344
3345 static test_return udp_buffered_set_test(memcached_st *memc)
3346 {
3347 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_BUFFER_REQUESTS, 1);
3348 return udp_set_test(memc);
3349 }
3350
3351 static test_return udp_set_too_big_test(memcached_st *memc)
3352 {
3353 memcached_return rc;
3354 char *key= "bar";
3355 char value[MAX_UDP_DATAGRAM_LENGTH];
3356 uint16_t *expected_ids= get_udp_request_ids(memc);
3357 rc= memcached_set(memc, key, strlen(key),
3358 value, MAX_UDP_DATAGRAM_LENGTH,
3359 (time_t)0, (uint32_t)0);
3360 assert(rc == MEMCACHED_WRITE_FAILURE);
3361 return post_udp_op_check(memc,expected_ids);
3362 }
3363
3364 test_return udp_delete_test(memcached_st *memc)
3365 {
3366 unsigned int x= 0;
3367 unsigned int num_iters= 1025; //request id rolls over at 1024
3368 for (x= 0; x < num_iters;x++)
3369 {
3370 memcached_return rc;
3371 char *key= "foo";
3372 uint16_t *expected_ids=get_udp_request_ids(memc);
3373 unsigned int server_key= memcached_generate_hash(memc, key, strlen(key));
3374 size_t init_offset= memc->hosts[server_key].write_buffer_offset;
3375 rc= memcached_delete(memc, key, strlen(key), 0);
3376 assert(rc == MEMCACHED_SUCCESS || rc == MEMCACHED_BUFFERED);
3377 if (rc == MEMCACHED_SUCCESS || memc->hosts[server_key].write_buffer_offset < init_offset)
3378 increment_request_id(&expected_ids[server_key]);
3379 if (rc == MEMCACHED_SUCCESS)
3380 assert(memc->hosts[server_key].write_buffer_offset == UDP_DATAGRAM_HEADER_LENGTH);
3381 else
3382 {
3383 assert(memc->hosts[server_key].write_buffer_offset != UDP_DATAGRAM_HEADER_LENGTH);
3384 assert(memc->hosts[server_key].write_buffer_offset <= MAX_UDP_DATAGRAM_LENGTH);
3385 }
3386 assert(post_udp_op_check(memc,expected_ids) == TEST_SUCCESS);
3387 }
3388 return TEST_SUCCESS;
3389 }
3390
3391 static test_return udp_buffered_delete_test(memcached_st *memc)
3392 {
3393 memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_BUFFER_REQUESTS, 1);
3394 return udp_delete_test(memc);
3395 }
3396
3397 test_return udp_verbosity_test(memcached_st *memc)
3398 {
3399 memcached_return rc;
3400 uint16_t *expected_ids= get_udp_request_ids(memc);
3401 unsigned int x;
3402 for (x= 0; x < memc->number_of_hosts;x++)
3403 increment_request_id(&expected_ids[x]);
3404
3405 rc= memcached_verbosity(memc,3);
3406 assert(rc == MEMCACHED_SUCCESS);
3407 return post_udp_op_check(memc,expected_ids);
3408 }
3409
3410 test_return udp_quit_test(memcached_st *memc)
3411 {
3412 uint16_t *expected_ids= get_udp_request_ids(memc);
3413 memcached_quit(memc);
3414 return post_udp_op_check(memc, expected_ids);
3415 }
3416
3417 test_return udp_flush_test(memcached_st *memc)
3418 {
3419 memcached_return rc;
3420 uint16_t *expected_ids= get_udp_request_ids(memc);
3421 unsigned int x;
3422 for (x= 0; x < memc->number_of_hosts;x++)
3423 increment_request_id(&expected_ids[x]);
3424
3425 rc= memcached_flush(memc,0);
3426 assert(rc == MEMCACHED_SUCCESS);
3427 return post_udp_op_check(memc,expected_ids);
3428 }
3429
3430 test_return udp_incr_test(memcached_st *memc)
3431 {
3432 memcached_return rc;
3433 char *key= "incr";
3434 char *value= "1";
3435 rc= memcached_set(memc, key, strlen(key),
3436 value, strlen(value),
3437 (time_t)0, (uint32_t)0);
3438
3439 assert(rc == MEMCACHED_SUCCESS);
3440 uint16_t *expected_ids= get_udp_request_ids(memc);
3441 unsigned int server_key= memcached_generate_hash(memc, key, strlen(key));
3442 increment_request_id(&expected_ids[server_key]);
3443 uint64_t newvalue;
3444 rc= memcached_increment(memc, key, strlen(key), 1, &newvalue);
3445 assert(rc == MEMCACHED_SUCCESS);
3446 return post_udp_op_check(memc, expected_ids);
3447 }
3448
3449 test_return udp_decr_test(memcached_st *memc)
3450 {
3451 memcached_return rc;
3452 char *key= "decr";
3453 char *value= "1";
3454 rc= memcached_set(memc, key, strlen(key),
3455 value, strlen(value),
3456 (time_t)0, (uint32_t)0);
3457
3458 assert(rc == MEMCACHED_SUCCESS);
3459 uint16_t *expected_ids= get_udp_request_ids(memc);
3460 unsigned int server_key= memcached_generate_hash(memc, key, strlen(key));
3461 increment_request_id(&expected_ids[server_key]);
3462 uint64_t newvalue;
3463 rc= memcached_decrement(memc, key, strlen(key), 1, &newvalue);
3464 assert(rc == MEMCACHED_SUCCESS);
3465 return post_udp_op_check(memc, expected_ids);
3466 }
3467
3468
3469 test_return udp_stat_test(memcached_st *memc)
3470 {
3471 memcached_stat_st * rv= NULL;
3472 memcached_return rc;
3473 char args[]= "";
3474 uint16_t *expected_ids = get_udp_request_ids(memc);
3475 rv = memcached_stat(memc, args, &rc);
3476 free(rv);
3477 assert(rc == MEMCACHED_NOT_SUPPORTED);
3478 return post_udp_op_check(memc, expected_ids);
3479 }
3480
3481 test_return udp_version_test(memcached_st *memc)
3482 {
3483 memcached_return rc;
3484 uint16_t *expected_ids = get_udp_request_ids(memc);
3485 rc = memcached_version(memc);
3486 assert(rc == MEMCACHED_NOT_SUPPORTED);
3487 return post_udp_op_check(memc, expected_ids);
3488 }
3489
3490 test_return udp_get_test(memcached_st *memc)
3491 {
3492 memcached_return rc;
3493 char *key= "foo";
3494 size_t vlen;
3495 uint16_t *expected_ids = get_udp_request_ids(memc);
3496 char *val= memcached_get(memc, key, strlen(key), &vlen, (uint32_t)0, &rc);
3497 assert(rc == MEMCACHED_NOT_SUPPORTED);
3498 assert(val == NULL);
3499 return post_udp_op_check(memc, expected_ids);
3500 }
3501
3502 test_return udp_mixed_io_test(memcached_st *memc)
3503 {
3504 test_st current_op;
3505 test_st mixed_io_ops [] ={
3506 {"udp_set_test", 0, udp_set_test},
3507 {"udp_set_too_big_test", 0, udp_set_too_big_test},
3508 {"udp_delete_test", 0, udp_delete_test},
3509 {"udp_verbosity_test", 0, udp_verbosity_test},
3510 {"udp_quit_test", 0, udp_quit_test},
3511 {"udp_flush_test", 0, udp_flush_test},
3512 {"udp_incr_test", 0, udp_incr_test},
3513 {"udp_decr_test", 0, udp_decr_test},
3514 {"udp_version_test", 0, udp_version_test}
3515 };
3516 unsigned int x= 0;
3517 for (x= 0; x < 500; x++)
3518 {
3519 current_op= mixed_io_ops[random() % 9];
3520 assert(current_op.function(memc) == TEST_SUCCESS);
3521 }
3522 return TEST_SUCCESS;
3523 }
3524
3525 test_st udp_setup_server_tests[] ={
3526 {"set_udp_behavior_test", 0, set_udp_behavior_test},
3527 {"add_tcp_server_udp_client_test", 0, add_tcp_server_udp_client_test},
3528 {"add_udp_server_tcp_client_test", 0, add_udp_server_tcp_client_test},
3529 {0, 0, 0}
3530 };
3531
3532 test_st upd_io_tests[] ={
3533 {"udp_set_test", 0, udp_set_test},
3534 {"udp_buffered_set_test", 0, udp_buffered_set_test},
3535 {"udp_set_too_big_test", 0, udp_set_too_big_test},
3536 {"udp_delete_test", 0, udp_delete_test},
3537 {"udp_buffered_delete_test", 0, udp_buffered_delete_test},
3538 {"udp_verbosity_test", 0, udp_verbosity_test},
3539 {"udp_quit_test", 0, udp_quit_test},
3540 {"udp_flush_test", 0, udp_flush_test},
3541 {"udp_incr_test", 0, udp_incr_test},
3542 {"udp_decr_test", 0, udp_decr_test},
3543 {"udp_stat_test", 0, udp_stat_test},
3544 {"udp_version_test", 0, udp_version_test},
3545 {"udp_get_test", 0, udp_get_test},
3546 {"udp_mixed_io_test", 0, udp_mixed_io_test},
3547 {0, 0, 0}
3548 };
3549
3550 /* Clean the server before beginning testing */
3551 test_st tests[] ={
3552 {"flush", 0, flush_test },
3553 {"init", 0, init_test },
3554 {"allocation", 0, allocation_test },
3555 {"server_list_null_test", 0, server_list_null_test},
3556 {"server_unsort", 0, server_unsort_test},
3557 {"server_sort", 0, server_sort_test},
3558 {"server_sort2", 0, server_sort2_test},
3559 {"clone_test", 0, clone_test },
3560 {"error", 0, error_test },
3561 {"set", 0, set_test },
3562 {"set2", 0, set_test2 },
3563 {"set3", 0, set_test3 },
3564 {"add", 1, add_test },
3565 {"replace", 1, replace_test },
3566 {"delete", 1, delete_test },
3567 {"get", 1, get_test },
3568 {"get2", 0, get_test2 },
3569 {"get3", 0, get_test3 },
3570 {"get4", 0, get_test4 },
3571 {"stats_servername", 0, stats_servername_test },
3572 {"increment", 0, increment_test },
3573 {"decrement", 0, decrement_test },
3574 {"quit", 0, quit_test },
3575 {"mget", 1, mget_test },
3576 {"mget_result", 1, mget_result_test },
3577 {"mget_result_alloc", 1, mget_result_alloc_test },
3578 {"mget_result_function", 1, mget_result_function },
3579 {"get_stats", 0, get_stats },
3580 {"add_host_test", 0, add_host_test },
3581 {"add_host_test_1", 0, add_host_test1 },
3582 {"get_stats_keys", 0, get_stats_keys },
3583 {"behavior_test", 0, get_stats_keys },
3584 {"callback_test", 0, get_stats_keys },
3585 {"version_string_test", 0, version_string_test},
3586 {"bad_key", 1, bad_key_test },
3587 {"memcached_server_cursor", 1, memcached_server_cursor_test },
3588 {"read_through", 1, read_through },
3589 {"delete_through", 1, delete_through },
3590 {"noreply", 1, noreply_test},
3591 {"analyzer", 1, analyzer_test},
3592 {0, 0, 0}
3593 };
3594
3595 test_st async_tests[] ={
3596 {"add", 1, add_wrapper },
3597 {0, 0, 0}
3598 };
3599
3600 test_st string_tests[] ={
3601 {"string static with null", 0, string_static_null },
3602 {"string alloc with null", 0, string_alloc_null },
3603 {"string alloc with 1K", 0, string_alloc_with_size },
3604 {"string alloc with malloc failure", 0, string_alloc_with_size_toobig },
3605 {"string append", 0, string_alloc_append },
3606 {"string append failure (too big)", 0, string_alloc_append_toobig },
3607 {0, 0, 0}
3608 };
3609
3610 test_st result_tests[] ={
3611 {"result static", 0, result_static},
3612 {"result alloc", 0, result_alloc},
3613 {0, 0, 0}
3614 };
3615
3616 test_st version_1_2_3[] ={
3617 {"append", 0, append_test },
3618 {"prepend", 0, prepend_test },
3619 {"cas", 0, cas_test },
3620 {"cas2", 0, cas2_test },
3621 {"append_binary", 0, append_binary_test },
3622 {0, 0, 0}
3623 };
3624
3625 test_st user_tests[] ={
3626 {"user_supplied_bug1", 0, user_supplied_bug1 },
3627 {"user_supplied_bug2", 0, user_supplied_bug2 },
3628 {"user_supplied_bug3", 0, user_supplied_bug3 },
3629 {"user_supplied_bug4", 0, user_supplied_bug4 },
3630 {"user_supplied_bug5", 1, user_supplied_bug5 },
3631 {"user_supplied_bug6", 1, user_supplied_bug6 },
3632 {"user_supplied_bug7", 1, user_supplied_bug7 },
3633 {"user_supplied_bug8", 1, user_supplied_bug8 },
3634 {"user_supplied_bug9", 1, user_supplied_bug9 },
3635 {"user_supplied_bug10", 1, user_supplied_bug10 },
3636 {"user_supplied_bug11", 1, user_supplied_bug11 },
3637 {"user_supplied_bug12", 1, user_supplied_bug12 },
3638 {"user_supplied_bug13", 1, user_supplied_bug13 },
3639 {"user_supplied_bug14", 1, user_supplied_bug14 },
3640 {"user_supplied_bug15", 1, user_supplied_bug15 },
3641 {"user_supplied_bug16", 1, user_supplied_bug16 },
3642 #ifndef __sun
3643 /*
3644 ** It seems to be something weird with the character sets..
3645 ** value_fetch is unable to parse the value line (iscntrl "fails"), so I
3646 ** guess I need to find out how this is supposed to work.. Perhaps I need
3647 ** to run the test in a specific locale (I tried zh_CN.UTF-8 without success,
3648 ** so just disable the code for now...).
3649 */
3650 {"user_supplied_bug17", 1, user_supplied_bug17 },
3651 #endif
3652 {"user_supplied_bug18", 1, user_supplied_bug18 },
3653 {"user_supplied_bug19", 1, user_supplied_bug19 },
3654 {"user_supplied_bug20", 1, user_supplied_bug20 },
3655 {0, 0, 0}
3656 };
3657
3658 test_st generate_tests[] ={
3659 {"generate_pairs", 1, generate_pairs },
3660 {"generate_data", 1, generate_data },
3661 {"get_read", 0, get_read },
3662 {"delete_generate", 0, delete_generate },
3663 {"generate_buffer_data", 1, generate_buffer_data },
3664 {"delete_buffer", 0, delete_buffer_generate},
3665 {"generate_data", 1, generate_data },
3666 {"mget_read", 0, mget_read },
3667 {"mget_read_result", 0, mget_read_result },
3668 {"mget_read_function", 0, mget_read_function },
3669 {"cleanup", 1, cleanup_pairs },
3670 {"generate_large_pairs", 1, generate_large_pairs },
3671 {"generate_data", 1, generate_data },
3672 {"generate_buffer_data", 1, generate_buffer_data },
3673 {"cleanup", 1, cleanup_pairs },
3674 {0, 0, 0}
3675 };
3676
3677 test_st consistent_tests[] ={
3678 {"generate_pairs", 1, generate_pairs },
3679 {"generate_data", 1, generate_data },
3680 {"get_read", 0, get_read_count },
3681 {"cleanup", 1, cleanup_pairs },
3682 {0, 0, 0}
3683 };
3684
3685 test_st consistent_weighted_tests[] ={
3686 {"generate_pairs", 1, generate_pairs },
3687 {"generate_data", 1, generate_data_with_stats },
3688 {"get_read", 0, get_read_count },
3689 {"cleanup", 1, cleanup_pairs },
3690 {0, 0, 0}
3691 };
3692
3693 collection_st collection[] ={
3694 {"udp_setup", init_udp, 0, udp_setup_server_tests},
3695 {"udp_io", init_udp, 0, upd_io_tests},
3696 {"udp_binary_io", binary_init_udp, 0, upd_io_tests},
3697 {"block", 0, 0, tests},
3698 {"binary", pre_binary, 0, tests},
3699 {"nonblock", pre_nonblock, 0, tests},
3700 {"nodelay", pre_nodelay, 0, tests},
3701 {"settimer", pre_settimer, 0, tests},
3702 {"md5", pre_md5, 0, tests},
3703 {"crc", pre_crc, 0, tests},
3704 {"hsieh", pre_hsieh, 0, tests},
3705 {"jenkins", pre_jenkins, 0, tests},
3706 {"fnv1_64", pre_hash_fnv1_64, 0, tests},
3707 {"fnv1a_64", pre_hash_fnv1a_64, 0, tests},
3708 {"fnv1_32", pre_hash_fnv1_32, 0, tests},
3709 {"fnv1a_32", pre_hash_fnv1a_32, 0, tests},
3710 {"ketama", pre_behavior_ketama, 0, tests},
3711 {"unix_socket", pre_unix_socket, 0, tests},
3712 {"unix_socket_nodelay", pre_nodelay, 0, tests},
3713 {"poll_timeout", poll_timeout, 0, tests},
3714 {"gets", enable_cas, 0, tests},
3715 {"consistent", enable_consistent, 0, tests},
3716 {"memory_allocators", set_memory_alloc, 0, tests},
3717 {"prefix", set_prefix, 0, tests},
3718 {"version_1_2_3", check_for_1_2_3, 0, version_1_2_3},
3719 {"string", 0, 0, string_tests},
3720 {"result", 0, 0, result_tests},
3721 {"async", pre_nonblock, 0, async_tests},
3722 {"async_binary", pre_nonblock_binary, 0, async_tests},
3723 {"user", 0, 0, user_tests},
3724 {"generate", 0, 0, generate_tests},
3725 {"generate_hsieh", pre_hsieh, 0, generate_tests},
3726 {"generate_ketama", pre_behavior_ketama, 0, generate_tests},
3727 {"generate_hsieh_consistent", enable_consistent, 0, generate_tests},
3728 {"generate_md5", pre_md5, 0, generate_tests},
3729 {"generate_murmur", pre_murmur, 0, generate_tests},
3730 {"generate_jenkins", pre_jenkins, 0, generate_tests},
3731 {"generate_nonblock", pre_nonblock, 0, generate_tests},
3732 {"consistent_not", 0, 0, consistent_tests},
3733 {"consistent_ketama", pre_behavior_ketama, 0, consistent_tests},
3734 {"consistent_ketama_weighted", pre_behavior_ketama_weighted, 0, consistent_weighted_tests},
3735 {0, 0, 0, 0}
3736 };
3737
3738 #define SERVERS_TO_CREATE 5
3739
3740 /* Prototypes for functions we will pass to test framework */
3741 void *world_create(void);
3742 void world_destroy(void *p);
3743
3744 void *world_create(void)
3745 {
3746 server_startup_st *construct;
3747
3748 construct= (server_startup_st *)malloc(sizeof(server_startup_st));
3749 memset(construct, 0, sizeof(server_startup_st));
3750 construct->count= SERVERS_TO_CREATE;
3751 construct->udp= 0;
3752 server_startup(construct);
3753
3754 return construct;
3755 }
3756
3757
3758 void world_destroy(void *p)
3759 {
3760 server_startup_st *construct= (server_startup_st *)p;
3761 memcached_server_st *servers= (memcached_server_st *)construct->servers;
3762 memcached_server_list_free(servers);
3763
3764 server_shutdown(construct);
3765 free(construct);
3766 }
3767
3768 void get_world(world_st *world)
3769 {
3770 world->collections= collection;
3771 world->create= world_create;
3772 world->destroy= world_destroy;
3773 }