Extend out testing for hosts.
authorBrian Aker <brian@tangent.org>
Fri, 10 Jun 2011 19:46:50 +0000 (12:46 -0700)
committerBrian Aker <brian@tangent.org>
Fri, 10 Jun 2011 19:46:50 +0000 (12:46 -0700)
libmemcached/connect.cc
libmemcached/error.cc
libmemcached/io.cc
libmemcached/purge.cc
libmemcached/return.h
libtest/test.c
tests/mem_functions.cc
tests/parser.cc
tests/parser.h

index eda4b88fac0b014905785c3dcdbd12733b1e9480..c9e91020e44f7dbe4d97bb638fcc63d6444a18b1 100644 (file)
@@ -52,7 +52,14 @@ static memcached_return_t connect_poll(memcached_server_st *ptr)
 
   while (--loop_max) // Should only loop on cases of ERESTART or EINTR
   {
-    error= poll(fds, 1, ptr->root->connect_timeout);
+    if (ptr->root->poll_timeout)
+    {
+      error= poll(fds, 1, ptr->root->connect_timeout);
+    }
+    else
+    {
+      error= 0;
+    }
 
     switch (error)
     {
@@ -76,6 +83,7 @@ static memcached_return_t connect_poll(memcached_server_st *ptr)
       }
     case 0:
       return MEMCACHED_TIMEOUT;
+
     default: // A real error occurred and we need to completely bail
       WATCHPOINT_ERRNO(get_socket_errno());
       switch (get_socket_errno())
@@ -457,8 +465,7 @@ static memcached_return_t network_connect(memcached_server_st *ptr)
     case EINPROGRESS: // nonblocking mode - first return
     case EALREADY: // nonblocking mode - subsequent returns
       {
-        memcached_return_t rc;
-        rc= connect_poll(ptr);
+        memcached_return_t rc= connect_poll(ptr);
 
         if (rc == MEMCACHED_TIMEOUT)
           timeout_error_occured= true;
index 01975956cfdc1b107d3cf7c0dc8cb627be999bf4..7914a165e9c8617cc57ba97c60c92d7697ceb223 100644 (file)
@@ -75,6 +75,11 @@ static void _set(memcached_st& memc, memcached_string_t *str, memcached_return_t
     rc= MEMCACHED_ERRNO;
   }
 
+  if (rc == MEMCACHED_ERRNO and local_errno == ENOTCONN)
+  {
+    rc= MEMCACHED_CONNECTION_FAILURE;
+  }
+
   memcached_error_t *error= (struct memcached_error_t *)libmemcached_malloc(&memc, sizeof(struct memcached_error_t));
   if (not error) // Bad business if this happens
     return;
@@ -84,16 +89,29 @@ static void _set(memcached_st& memc, memcached_string_t *str, memcached_return_t
   error->rc= rc;
   error->local_errno= local_errno;
 
-  if (str)
+  if (str and local_errno)
+  {
+    error->size= (int)snprintf(error->message, MAX_ERROR_LENGTH, "%s(%s), %.*s -> %s", 
+                               memcached_strerror(&memc, rc), 
+                               strerror(local_errno),
+                               int(error->size), str->c_str, at);
+  }
+  else if (local_errno)
+  {
+    error->size= (int)snprintf(error->message, MAX_ERROR_LENGTH, "%s(%s) -> %s", 
+                               memcached_strerror(&memc, rc), 
+                               strerror(local_errno), at);
+  }
+  else if (str)
   {
-    size_t length= str->size > (size_t)MAX_ERROR_LENGTH ? MAX_ERROR_LENGTH : str->size;
-    error->size= length;
-    memcpy(error->message, str->c_str, error->size);
-    error->message[error->size]= 0;
+    error->size= (int)snprintf(error->message, MAX_ERROR_LENGTH, "%s, %.*s -> %s", 
+                               memcached_strerror(&memc, rc), 
+                               int(error->size), str->c_str, at);
   }
   else
   {
-    error->size= 0;
+    error->size= (int)snprintf(error->message, MAX_ERROR_LENGTH, "%s -> %s", 
+                               memcached_strerror(&memc, rc), at);
   }
 
   error->next= memc.error_messages;
index 3a3cd45be059f53af9a3d73a5d1d5de4b2270841..d2c3a03d33a73e535e4fac305daa94d7365e5408 100644 (file)
@@ -37,7 +37,7 @@
  */
 
 
-#include "libmemcached/common.h"
+#include <libmemcached/common.h>
 
 typedef enum {
   MEM_READ,
@@ -80,13 +80,22 @@ static memcached_return_t io_wait(memcached_server_write_instance_st ptr,
   {
     memcached_return_t rc= memcached_purge(ptr);
     if (rc != MEMCACHED_SUCCESS && rc != MEMCACHED_STORED)
+    {
       return MEMCACHED_FAILURE;
+    }
   }
 
   size_t loop_max= 5;
   while (--loop_max) // While loop is for ERESTART or EINTR
   {
-    error= poll(&fds, 1, ptr->root->poll_timeout);
+    if (ptr->root->poll_timeout) // Mimic 0 causes timeout behavior (not all platforms do this)
+    {
+      error= poll(&fds, 1, ptr->root->poll_timeout);
+    }
+    else
+    {
+      error= 0;
+    }
 
     switch (error)
     {
@@ -95,8 +104,10 @@ static memcached_return_t io_wait(memcached_server_write_instance_st ptr,
       WATCHPOINT_IF_LABELED_NUMBER(!read_or_write && loop_max < 4, "write() times we had to loop, decremented down from 5", loop_max);
 
       return MEMCACHED_SUCCESS;
+
     case 0: // Timeout occured, we let the while() loop do its thing.
-      return MEMCACHED_TIMEOUT;
+      return memcached_set_error(*ptr, MEMCACHED_TIMEOUT, MEMCACHED_AT);
+
     default:
       WATCHPOINT_ERRNO(get_socket_errno());
       switch (get_socket_errno())
@@ -106,6 +117,7 @@ static memcached_return_t io_wait(memcached_server_write_instance_st ptr,
 #endif
       case EINTR:
         break;
+
       default:
         if (fds.revents & POLLERR)
         {
@@ -120,7 +132,7 @@ static memcached_return_t io_wait(memcached_server_write_instance_st ptr,
         }
         memcached_quit_server(ptr, true);
 
-        return MEMCACHED_FAILURE;
+        return memcached_set_errno(*ptr, get_socket_errno(), MEMCACHED_AT);
       }
     }
   }
@@ -130,7 +142,7 @@ static memcached_return_t io_wait(memcached_server_write_instance_st ptr,
   ptr->cached_errno= get_socket_errno();
   memcached_quit_server(ptr, true);
 
-  return MEMCACHED_FAILURE;
+  return memcached_set_error(*ptr, MEMCACHED_FAILURE, MEMCACHED_AT);
 }
 
 memcached_return_t memcached_io_wait_for_write(memcached_server_write_instance_st ptr)
@@ -290,6 +302,7 @@ memcached_return_t memcached_io_read(memcached_server_write_instance_st ptr,
 #endif
             if ((rc= io_wait(ptr, MEM_READ)) == MEMCACHED_SUCCESS)
               continue;
+
             /* fall through */
 
           default:
@@ -582,12 +595,15 @@ static ssize_t io_flush(memcached_server_write_instance_st ptr,
   // UDP Sanity check, make sure that we are not sending somthing too big
   if (ptr->type == MEMCACHED_CONNECTION_UDP && write_length > MAX_UDP_DATAGRAM_LENGTH)
   {
+    *error= MEMCACHED_WRITE_FAILURE;
     return -1;
   }
 
   if (ptr->write_buffer_offset == 0 || (ptr->type == MEMCACHED_CONNECTION_UDP
                                         && ptr->write_buffer_offset == UDP_DATAGRAM_HEADER_LENGTH))
+  {
     return 0;
+  }
 
   /* Looking for memory overflows */
 #if defined(DEBUG)
@@ -641,15 +657,19 @@ static ssize_t io_flush(memcached_server_write_instance_st ptr,
               process_input_buffer(ptr))
             continue;
 
-          memcached_return_t rc;
-          rc= io_wait(ptr, MEM_WRITE);
-
-          if (rc == MEMCACHED_SUCCESS || rc == MEMCACHED_TIMEOUT)
+          memcached_return_t rc= io_wait(ptr, MEM_WRITE);
+          if (memcached_success(rc))
           {
             continue;
           }
+          else if (rc == MEMCACHED_TIMEOUT)
+          {
+            *error= memcached_set_error(*ptr, MEMCACHED_TIMEOUT, MEMCACHED_AT);
+            return -1;
+          }
 
           memcached_quit_server(ptr, true);
+          *error= memcached_set_errno(*ptr, get_socket_errno(), MEMCACHED_AT);
           return -1;
         }
       case ENOTCONN:
@@ -662,10 +682,11 @@ static ssize_t io_flush(memcached_server_write_instance_st ptr,
       }
     }
 
-    if (ptr->type == MEMCACHED_CONNECTION_UDP &&
+    if (ptr->type == MEMCACHED_CONNECTION_UDP and
         (size_t)sent_length != write_length)
     {
       memcached_quit_server(ptr, true);
+      *error= memcached_set_error(*ptr, MEMCACHED_WRITE_FAILURE, MEMCACHED_AT);
       return -1;
     }
 
index 07cd135f56c939281ae786bdd32372ea97e4b985..36a33ae987b46feb06bba06734312e86dc95b5bd 100644 (file)
@@ -2,7 +2,6 @@
 
 memcached_return_t memcached_purge(memcached_server_write_instance_st ptr)
 {
-  uint32_t x;
   memcached_return_t ret= MEMCACHED_SUCCESS;
   memcached_st *root= (memcached_st *)ptr->root;
 
@@ -26,7 +25,7 @@ memcached_return_t memcached_purge(memcached_server_write_instance_st ptr)
   {
     memcached_set_purging(root, true);
 
-    return MEMCACHED_WRITE_FAILURE;
+    return memcached_set_error(*ptr, MEMCACHED_WRITE_FAILURE, MEMCACHED_AT);
   }
   WATCHPOINT_ASSERT(ptr->fd != -1);
 
@@ -48,7 +47,7 @@ memcached_return_t memcached_purge(memcached_server_write_instance_st ptr)
     result_ptr= memcached_result_create(root, &result);
     WATCHPOINT_ASSERT(result_ptr);
 
-    for (x= 0; x < no_msg; x++)
+    for (uint32_t x= 0; x < no_msg; x++)
     {
       memcached_result_reset(result_ptr);
       memcached_return_t rc= memcached_read_one_response(ptr, buffer,
@@ -62,8 +61,9 @@ memcached_return_t memcached_purge(memcached_server_write_instance_st ptr)
       if (rc== MEMCACHED_PROTOCOL_ERROR || rc == MEMCACHED_UNKNOWN_READ_FAILURE)
       {
         WATCHPOINT_ERROR(rc);
-        ret = rc;
+        ret= rc;
         memcached_io_reset(ptr);
+        memcached_set_error(*ptr, rc, MEMCACHED_AT);
       }
 
       if (ptr->root->callbacks != NULL)
index 57c0a19f0e9770c7c5364149d3a60261a0fcb102..35ad69d9332450af1ecd129e9cc1dfabeb6a50a3 100644 (file)
@@ -40,8 +40,8 @@ enum memcached_return_t {
   MEMCACHED_SUCCESS,
   MEMCACHED_FAILURE,
   MEMCACHED_HOST_LOOKUP_FAILURE, // getaddrinfo() and getnameinfo() only
-  MEMCACHED_CONNECTION_FAILURE,  // DEPRECATED
-  MEMCACHED_CONNECTION_BIND_FAILURE,  // DEPRECATED
+  MEMCACHED_CONNECTION_FAILURE,
+  MEMCACHED_CONNECTION_BIND_FAILURE,  // DEPRECATED, see MEMCACHED_HOST_LOOKUP_FAILURE
   MEMCACHED_WRITE_FAILURE,
   MEMCACHED_READ_FAILURE,
   MEMCACHED_UNKNOWN_READ_FAILURE,
index afb2b96522ce4c1f582e4fa6771c5c2bb2735c31..d54dc92b9836347a533685a942ba74bb7324b5b3 100644 (file)
@@ -178,10 +178,21 @@ int main(int argc, char *argv[])
   }
 
   if (argc > 1)
+  {
     collection_to_run= argv[1];
+  }
+  else if (getenv("TEST_COLLECTION"))
+  {
+    collection_to_run= getenv("TEST_COLLECTION");
+  }
+
+  if (collection_to_run)
+    printf("Only testing %s\n", collection_to_run);
 
   if (argc == 3)
+  {
     wildcard= argv[2];
+  }
 
   for (next= collection; next->name; next++)
   {
index b48f0d082ff915cacc7b31978527ed58ab6661cd..093721b5cd29e52c64409b075b167cfeab4eaf7e 100644 (file)
@@ -5757,7 +5757,7 @@ static test_return_t regression_bug_583031(memcached_st *)
   test_false(value);
   test_compare(0, length);
 
-  test_true_got(rc == MEMCACHED_TIMEOUT || rc == MEMCACHED_ERRNO || rc == MEMCACHED_FAILURE, memcached_strerror(memc, rc));
+  test_compare_got(MEMCACHED_TIMEOUT, rc, memcached_strerror(memc, rc));
 
   memcached_free(memc);
 
@@ -6114,7 +6114,8 @@ test_st regression_tests[]= {
   {"lp:?", 1, (test_callback_fn)regression_bug_ },
   {"lp:728286", 1, (test_callback_fn)regression_bug_728286 },
   {"lp:581030", 1, (test_callback_fn)regression_bug_581030 },
-  {"lp:71231153", 1, (test_callback_fn)regression_bug_71231153 },
+  {"lp:71231153 connect()", 1, (test_callback_fn)regression_bug_71231153_connect },
+  {"lp:71231153 poll()", 1, (test_callback_fn)regression_bug_71231153_poll },
   {0, 0, (test_callback_fn)0}
 };
 
index 113d6e00df3b4c61fc45378c09c6cf5523a1719e..13561bcc29b03e19719e8ed417f26ac2902a0e74 100644 (file)
@@ -547,24 +547,53 @@ test_return_t test_hostname_port_weight(memcached_st *)
   return TEST_SUCCESS;
 }
 
-test_return_t regression_bug_71231153(memcached_st *)
+/*
+  By setting the timeout value to zero, we force poll() to return immediatly.
+*/
+test_return_t regression_bug_71231153_connect(memcached_st *)
 {
   if (libmemcached_util_ping("10.0.2.252", 0, NULL)) // If for whatever reason someone has a host at this address, skip
     return TEST_SKIPPED;
 
-  memcached_st *memc= memcached(memcached_literal_param("--SERVER=10.0.2.252 --CONNECT-TIMEOUT=1 --POLL-TIMEOUT=1"));
-  test_true(memc);
-  test_compare(1, memc->connect_timeout);
-  test_compare(1, memc->poll_timeout);
+  { // Test the connect-timeout, on a bad host we should get MEMCACHED_CONNECTION_FAILURE
+    memcached_st *memc= memcached(memcached_literal_param("--SERVER=10.0.2.252 --CONNECT-TIMEOUT=0"));
+    test_true(memc);
+    test_compare(0, memc->connect_timeout);
+    test_compare(MEMCACHED_DEFAULT_TIMEOUT, memc->poll_timeout);
 
-  memcached_return_t rc;
-  size_t value_len;
-  char *value= memcached_get(memc, memcached_literal_param("test"), &value_len, NULL, &rc);
-  test_false(value);
-  test_compare(0, value_len);
-  test_true_got(rc == MEMCACHED_TIMEOUT or rc == MEMCACHED_FAILURE or rc == MEMCACHED_ERRNO, memcached_strerror(memc, rc));
+    memcached_return_t rc;
+    size_t value_len;
+    char *value= memcached_get(memc, memcached_literal_param("test"), &value_len, NULL, &rc);
+    test_false(value);
+    test_compare(0, value_len);
+    test_compare_got(MEMCACHED_CONNECTION_FAILURE, rc, memcached_strerror(NULL, rc));
 
-  memcached_free(memc);
+    memcached_free(memc);
+  }
+
+  return TEST_SUCCESS;
+}
+
+test_return_t regression_bug_71231153_poll(memcached_st *)
+{
+  if (libmemcached_util_ping("10.0.2.252", 0, NULL)) // If for whatever reason someone has a host at this address, skip
+    return TEST_SKIPPED;
+
+  { // Test the poll timeout, on a bad host we should get MEMCACHED_CONNECTION_FAILURE
+    memcached_st *memc= memcached(memcached_literal_param("--SERVER=10.0.2.252 --POLL-TIMEOUT=0"));
+    test_true(memc);
+    test_compare(MEMCACHED_DEFAULT_CONNECT_TIMEOUT, memc->connect_timeout);
+    test_compare(0, memc->poll_timeout);
+
+    memcached_return_t rc;
+    size_t value_len;
+    char *value= memcached_get(memc, memcached_literal_param("test"), &value_len, NULL, &rc);
+    test_false(value);
+    test_compare(0, value_len);
+    test_compare_got(MEMCACHED_TIMEOUT, rc, memcached_strerror(NULL, rc));
+
+    memcached_free(memc);
+  }
 
   return TEST_SUCCESS;
 }
index 98d3c1be389f55de04ede3fcb875de4a24f276ae..15d57a64683317cb2d7c55dc8a8e5b7a4cd5bcdd 100644 (file)
@@ -101,7 +101,10 @@ LIBTEST_INTERNAL_API
 test_return_t test_hostname_port_weight(memcached_st *);
 
 LIBTEST_INTERNAL_API
-test_return_t regression_bug_71231153(memcached_st *);
+test_return_t regression_bug_71231153_connect(memcached_st *);
+
+LIBTEST_INTERNAL_API
+test_return_t regression_bug_71231153_poll(memcached_st *);
 
 #ifdef __cplusplus
 }