memcached_st *clone;
clone= memcached_clone(NULL, memc);
assert(clone);
+
+ assert(clone->call_free == memc->call_free);
+ assert(clone->call_malloc == memc->call_malloc);
+ assert(clone->call_realloc == memc->call_realloc);
+ assert(clone->connect_timeout == memc->connect_timeout);
+ assert(clone->delete_trigger == memc->delete_trigger);
+ assert(clone->distribution == memc->distribution);
+ assert(clone->flags == memc->flags);
+ assert(clone->get_key_failure == memc->get_key_failure);
+ assert(clone->hash == memc->hash);
+ assert(clone->hash_continuum == memc->hash_continuum);
+ assert(clone->io_bytes_watermark == memc->io_bytes_watermark);
+ assert(clone->io_msg_watermark == memc->io_msg_watermark);
+ assert(clone->on_cleanup == memc->on_cleanup);
+ assert(clone->on_clone == memc->on_clone);
+ assert(clone->poll_timeout == memc->poll_timeout);
+ assert(clone->rcv_timeout == memc->rcv_timeout);
+ assert(clone->recv_size == memc->recv_size);
+ assert(clone->retry_timeout == memc->retry_timeout);
+ assert(clone->send_size == memc->send_size);
+ assert(clone->server_failure_limit == memc->server_failure_limit);
+ assert(clone->snd_timeout == memc->snd_timeout);
+ assert(clone->user_data == memc->user_data);
+
memcached_free(clone);
}
return 0;
}
+/*
+** There was a problem of leaking filedescriptors in the initial release
+** of MacOSX 10.5. This test case triggers the problem. On some Solaris
+** systems it seems that the kernel is slow on reclaiming the resources
+** because the connects starts to time out (the test doesn't do much
+** anyway, so just loop 10 iterations)
+*/
static test_return add_wrapper(memcached_st *memc)
{
unsigned int x;
+ unsigned int max= 10000;
+#ifdef __sun
+ max= 10;
+#endif
- for (x= 0; x < 10000; x++)
+ for (x= 0; x < max; x++)
add_test(memc);
return 0;
return 0;
}
+/*
+ * This test verifies that memcached_read_one_response doesn't try to
+ * dereference a NIL-pointer if you issue a multi-get and don't read out all
+ * responses before you execute a storage command.
+ */
+static test_return get_test5(memcached_st *memc)
+{
+ /*
+ ** Request the same key twice, to ensure that we hash to the same server
+ ** (so that we have multiple response values queued up) ;-)
+ */
+ char *keys[]= { "key", "key" };
+ size_t lengths[]= { 3, 3 };
+ uint32_t flags;
+ size_t rlen;
+
+ memcached_return rc= memcached_set(memc, keys[0], lengths[0],
+ keys[0], lengths[0], 0, 0);
+ assert(rc == MEMCACHED_SUCCESS);
+ rc= memcached_mget(memc, keys, lengths, 2);
+
+ memcached_result_st results_obj;
+ memcached_result_st *results;
+ results=memcached_result_create(memc, &results_obj);
+ assert(results);
+ results=memcached_fetch_result(memc, &results_obj, &rc);
+ assert(results);
+ memcached_result_free(&results_obj);
+
+ /* Don't read out the second result, but issue a set instead.. */
+ rc= memcached_set(memc, keys[0], lengths[0], keys[0], lengths[0], 0, 0);
+ assert(rc == MEMCACHED_SUCCESS);
+
+ char *val= memcached_get_by_key(memc, keys[0], lengths[0], "yek", 3,
+ &rlen, &flags, &rc);
+ assert(val == NULL);
+ assert(rc == MEMCACHED_NOTFOUND);
+ val= memcached_get(memc, keys[0], lengths[0], &rlen, &flags, &rc);
+ assert(val != NULL);
+ assert(rc == MEMCACHED_SUCCESS);
+ free(val);
+
+ return TEST_SUCCESS;
+}
+
/* Do not copy the style of this code, I just access hosts to testthis function */
static test_return stats_servername_test(memcached_st *memc)
{
{
memcached_return rc;
int value;
- int i;
+ int x;
memcached_server_st *server_pool;
memcached_st *memc;
assert(memcached_generate_hash(memc, (char *)"VDEAAAAA", 8) == memc->continuum[0].index);
/* verify the standard ketama set. */
- for (i= 0; i < 99; i++)
+ for (x= 0; x < 99; x++)
{
- uint32_t server_idx = memcached_generate_hash(memc, test_cases[i].key, strlen(test_cases[i].key));
+ uint32_t server_idx = memcached_generate_hash(memc, test_cases[x].key, strlen(test_cases[x].key));
char *hostname = memc->hosts[server_idx].hostname;
- assert(strcmp(hostname, test_cases[i].server) == 0);
+ assert(strcmp(hostname, test_cases[x].server) == 0);
}
memcached_server_list_free(server_pool);
return TEST_SUCCESS;
}
-static void increment_request_id(uint16_t *id) {
+static void increment_request_id(uint16_t *id)
+{
(*id)++;
if ((*id & UDP_REQUEST_ID_THREAD_MASK) != 0)
*id= 0;
{
uint16_t *ids= malloc(sizeof(uint16_t) * memc->number_of_hosts);
assert(ids != NULL);
- unsigned int i;
- for (i= 0; i < memc->number_of_hosts; i++)
- ids[i]= get_udp_datagram_request_id((struct udp_datagram_header_st *) memc->hosts[i].write_buffer);
+ unsigned int x;
+ for (x= 0; x < memc->number_of_hosts; x++)
+ ids[x]= get_udp_datagram_request_id((struct udp_datagram_header_st *) memc->hosts[x].write_buffer);
return ids;
}
-static test_return post_udp_op_check(memcached_st *memc, uint16_t *expected_req_ids) {
- unsigned int i;
+static test_return post_udp_op_check(memcached_st *memc, uint16_t *expected_req_ids)
+{
+ unsigned int x;
memcached_server_st *cur_server = memc->hosts;
uint16_t *cur_req_ids = get_udp_request_ids(memc);
- for (i= 0; i < memc->number_of_hosts; i++)
+ for (x= 0; x < memc->number_of_hosts; x++)
{
- assert(cur_server[i].cursor_active == 0);
- assert(cur_req_ids[i] == expected_req_ids[i]);
+ assert(cur_server[x].cursor_active == 0);
+ assert(cur_req_ids[x] == expected_req_ids[x]);
}
free(expected_req_ids);
free(cur_req_ids);
static memcached_return init_udp(memcached_st *memc)
{
memcached_version(memc);
- if (memc->hosts[0].major_version != 1 || memc->hosts[0].minor_version != 2)
+ /* For the time being, only support udp test for >= 1.2.6 && < 1.3 */
+ if (memc->hosts[0].major_version != 1 || memc->hosts[0].minor_version != 2
+ || memc->hosts[0].micro_version < 6)
return MEMCACHED_FAILURE;
uint32_t num_hosts= memc->number_of_hosts;
- unsigned int i= 0;
+ unsigned int x= 0;
memcached_server_st servers[num_hosts];
memcpy(servers, memc->hosts, sizeof(memcached_server_st) * num_hosts);
memc->number_of_hosts= 0;
memcached_behavior_set(memc, MEMCACHED_BEHAVIOR_USE_UDP, 1);
- for (i= 0; i < num_hosts; i++)
+ for (x= 0; x < num_hosts; x++)
{
- assert(memcached_server_add_udp(memc, servers[i].hostname, servers[i].port) == MEMCACHED_SUCCESS);
- assert(memc->hosts[i].write_buffer_offset == UDP_DATAGRAM_HEADER_LENGTH);
+ assert(memcached_server_add_udp(memc, servers[x].hostname, servers[x].port) == MEMCACHED_SUCCESS);
+ assert(memc->hosts[x].write_buffer_offset == UDP_DATAGRAM_HEADER_LENGTH);
}
return MEMCACHED_SUCCESS;
}
static test_return udp_set_test(memcached_st *memc)
{
- unsigned int i= 0;
+ unsigned int x= 0;
unsigned int num_iters= 1025; //request id rolls over at 1024
- for (i= 0; i < num_iters;i++)
+ for (x= 0; x < num_iters;x++)
{
memcached_return rc;
char *key= "foo";
memc->hosts[server_key].write_buffer_offset < init_offset)
increment_request_id(&expected_ids[server_key]);
- if (rc == MEMCACHED_SUCCESS) {
+ if (rc == MEMCACHED_SUCCESS)
+ {
assert(memc->hosts[server_key].write_buffer_offset == UDP_DATAGRAM_HEADER_LENGTH);
- } else {
+ }
+ else
+ {
assert(memc->hosts[server_key].write_buffer_offset != UDP_DATAGRAM_HEADER_LENGTH);
assert(memc->hosts[server_key].write_buffer_offset <= MAX_UDP_DATAGRAM_LENGTH);
}
test_return udp_delete_test(memcached_st *memc)
{
- unsigned int i= 0;
+ unsigned int x= 0;
unsigned int num_iters= 1025; //request id rolls over at 1024
- for (i= 0; i < num_iters;i++)
+ for (x= 0; x < num_iters;x++)
{
memcached_return rc;
char *key= "foo";
{"udp_decr_test", 0, udp_decr_test},
{"udp_version_test", 0, udp_version_test}
};
- unsigned int i= 0;
- for (i= 0; i < 500; i++)
+ unsigned int x= 0;
+ for (x= 0; x < 500; x++)
{
current_op= mixed_io_ops[random() % 9];
assert(current_op.function(memc) == TEST_SUCCESS);
{"get2", 0, get_test2 },
{"get3", 0, get_test3 },
{"get4", 0, get_test4 },
+ {"partial mget", 0, get_test5 },
{"stats_servername", 0, stats_servername_test },
{"increment", 0, increment_test },
{"decrement", 0, decrement_test },