* Added option to memcache_behavior_set() so that poll() can be timed out.
* Fixed memory leak in case of using memcached_fetch_result() where no
value was returned.
+ * Bug fixed in memcached_connect() which would cause servers that
+ did not need to be enabled to be enabled (performance issue).
0.10 Tue Nov 20 23:22:31 PST 2007
* Added append binary test.
typedef enum {
MEMCACHED_NOT_ALLOCATED,
MEMCACHED_ALLOCATED,
+ MEMCACHED_USED,
} memcached_allocated;
struct memcached_server_st {
if (ptr->is_allocated == MEMCACHED_ALLOCATED)
free(ptr);
else
- memset(ptr, 0, sizeof(memcached_st));
+ ptr->is_allocated= MEMCACHED_USED;
}
/*
/* Old connection junk still is in the structure */
WATCHPOINT_ASSERT(ptr->hosts[server_key].stack_responses == 0);
- if (ptr->hosts[server_key].servAddr.sin_family == 0)
+ if (ptr->hosts[server_key].sockaddr_inited == MEMCACHED_NOT_ALLOCATED ||
+ (!(ptr->flags & MEM_USE_CACHE_LOOKUPS)))
{
memcached_return rc;
rc= set_hostinfo(&ptr->hosts[server_key]);
if (rc != MEMCACHED_SUCCESS)
return rc;
+ ptr->hosts[server_key].sockaddr_inited= MEMCACHED_ALLOCATED;
}
/* Create the socket */
return MEMCACHED_NO_SERVERS;
/* We need to clean up the multi startup piece */
- if (server_key)
+ switch (ptr->hosts[server_key].type)
{
+ case MEMCACHED_CONNECTION_UNKNOWN:
+ WATCHPOINT_ASSERT(0);
+ rc= MEMCACHED_NOT_SUPPORTED;
+ break;
+ case MEMCACHED_CONNECTION_UDP:
+ rc= udp_connect(ptr, server_key);
+ break;
+ case MEMCACHED_CONNECTION_TCP:
rc= tcp_connect(ptr, server_key);
- switch (ptr->hosts[server_key].type)
- {
- case MEMCACHED_CONNECTION_UNKNOWN:
- WATCHPOINT_ASSERT(0);
- rc= MEMCACHED_NOT_SUPPORTED;
- break;
- case MEMCACHED_CONNECTION_UDP:
- rc= udp_connect(ptr, server_key);
- break;
- case MEMCACHED_CONNECTION_TCP:
- rc= tcp_connect(ptr, server_key);
- break;
- case MEMCACHED_CONNECTION_UNIX_SOCKET:
- rc= unix_socket_connect(ptr, server_key);
- break;
- }
-
- if (rc != MEMCACHED_SUCCESS)
- WATCHPOINT_ERROR(rc);
+ break;
+ case MEMCACHED_CONNECTION_UNIX_SOCKET:
+ rc= unix_socket_connect(ptr, server_key);
+ break;
}
- else
- {
- unsigned int x;
-
- for (x= 0; x < ptr->number_of_hosts; x++)
- {
- memcached_return possible_rc;
- possible_rc= MEMCACHED_NOT_SUPPORTED; /* Remove warning */
+ if (rc != MEMCACHED_SUCCESS)
+ WATCHPOINT_ERROR(rc);
- switch (ptr->hosts[x].type)
- {
- case MEMCACHED_CONNECTION_UNKNOWN:
- WATCHPOINT_ASSERT(0);
- possible_rc= MEMCACHED_NOT_SUPPORTED;
- break;
- case MEMCACHED_CONNECTION_UDP:
- possible_rc= udp_connect(ptr, x);
- break;
- case MEMCACHED_CONNECTION_TCP:
- possible_rc= tcp_connect(ptr, x);
- break;
- case MEMCACHED_CONNECTION_UNIX_SOCKET:
- possible_rc= unix_socket_connect(ptr, x);
- break;
- }
- rc= MEMCACHED_SUCCESS;
-
- if (possible_rc != MEMCACHED_SUCCESS)
- {
- WATCHPOINT_ERROR(possible_rc);
- rc= MEMCACHED_SOME_ERRORS;
- }
- }
- }
LIBMEMCACHED_MEMCACHED_CONNECT_END();
return rc;
char buffer[MEMCACHED_DEFAULT_COMMAND_SIZE];
LIBMEMCACHED_MEMCACHED_FLUSH_START();
- rc= memcached_connect(ptr, 0);
-
- if (rc == MEMCACHED_NO_SERVERS)
- return rc;
-
- if (rc != MEMCACHED_SUCCESS)
- rc= MEMCACHED_SOME_ERRORS;
+ if (ptr->number_of_hosts == 0)
+ return MEMCACHED_NO_SERVERS;
for (x= 0; x < ptr->number_of_hosts; x++)
{
send_length= snprintf(buffer, MEMCACHED_DEFAULT_COMMAND_SIZE,
"flush_all\r\n");
- if (send_length >= MEMCACHED_DEFAULT_COMMAND_SIZE)
- return MEMCACHED_WRITE_FAILURE;
-
rc= memcached_do(ptr, x, buffer, send_length, 1);
- if (rc != MEMCACHED_SUCCESS)
- goto error;
-
- rc= memcached_response(ptr, buffer, MEMCACHED_DEFAULT_COMMAND_SIZE, x);
- if (rc != MEMCACHED_SUCCESS)
- rc= MEMCACHED_SOME_ERRORS;
+ if (rc == MEMCACHED_SUCCESS)
+ (void)memcached_response(ptr, buffer, MEMCACHED_DEFAULT_COMMAND_SIZE, x);
}
-error:
LIBMEMCACHED_MEMCACHED_FLUSH_END();
- return rc;
+ return MEMCACHED_SUCCESS;
}
if (result == NULL)
result= memcached_result_create(ptr, NULL);
+ WATCHPOINT_ASSERT(result->value.is_allocated != MEMCACHED_USED);
+
while (ptr->cursor_server < ptr->number_of_hosts)
{
if (!ptr->hosts[ptr->cursor_server].cursor_active)
{
return result;
}
-
}
error:
- memcached_result_free(result);
+ memcached_string_reset(&result->value);
return NULL;
}
return 0;
}
else
- return hash % ptr->number_of_hosts;
+ {
+ unsigned int server_key;
+
+ server_key= hash % ptr->number_of_hosts;
+
+ return server_key;
+ }
}
static uint64_t internal_generate_hash(char *key, size_t key_length)
host->type= type;
host->read_ptr= host->read_buffer;
host->write_ptr= host->write_buffer;
+ host->sockaddr_inited= MEMCACHED_NOT_ALLOCATED;
}
memcached_return memcached_server_push(memcached_st *ptr, memcached_server_st *list)
void memcached_result_free(memcached_result_st *ptr)
{
+ if (ptr == NULL)
+ return;
+
memcached_string_free(&ptr->value);
if (ptr->is_allocated == MEMCACHED_ALLOCATED)
free(ptr);
+ else
+ ptr->is_allocated= MEMCACHED_USED;
}
if (key_length == 0)
return MEMCACHED_NO_KEY_PROVIDED;
- /* Leaving this WATCHPOINT_ASSERT in since only a library fubar could blow this */
-#ifdef NOT_DONE
- if (!(ptr->flags & MEM_NO_BLOCK) && ptr->write_buffer_offset != 0)
- WATCHPOINT_ASSERT(0);
-#endif
-
if (ptr->hosts == NULL || ptr->number_of_hosts == 0)
return MEMCACHED_NO_SERVERS;
{
memcached_return rc;
+ WATCHPOINT_ASSERT(string->is_allocated != MEMCACHED_USED);
+
rc= memcached_string_check(string, 1);
if (rc != MEMCACHED_SUCCESS)
{
memcached_return rc;
+ WATCHPOINT_ASSERT(string->is_allocated != MEMCACHED_USED);
+
rc= memcached_string_check(string, length);
if (rc != MEMCACHED_SUCCESS)
size_t memcached_string_backspace(memcached_string_st *string, size_t remove)
{
+ WATCHPOINT_ASSERT(string->is_allocated != MEMCACHED_USED);
+
if (string->end - string->string > remove)
{
size_t difference;
char *memcached_string_c_copy(memcached_string_st *string)
{
char *c_ptr;
+
+ WATCHPOINT_ASSERT(string->is_allocated != MEMCACHED_USED);
+
c_ptr= (char *)malloc(memcached_string_length(string) * sizeof(char));
if (!c_ptr)
return NULL;
memcached_return memcached_string_reset(memcached_string_st *string)
{
+ WATCHPOINT_ASSERT(string->is_allocated != MEMCACHED_USED);
string->end= string->string;
return MEMCACHED_SUCCESS;
}
-void memcached_string_free(memcached_string_st *string)
+void memcached_string_free(memcached_string_st *ptr)
{
- if (string->string)
- free(string->string);
- if (string->is_allocated == MEMCACHED_ALLOCATED)
- free(string);
+ if (ptr == NULL)
+ return;
+
+ if (ptr->string)
+ free(ptr->string);
+
+ if (ptr->is_allocated == MEMCACHED_ALLOCATED)
+ free(ptr);
+ else
+ ptr->is_allocated= MEMCACHED_USED;
}
{
assert(results);
}
+
while ((results= memcached_fetch_result(memc, &results_obj, &rc)) != NULL)
assert(!results);
assert(rc == MEMCACHED_NOTFOUND);