Module: sip-router
Branch: master
Commit: 141808e9c0789e56f29297e2d2c185e091ebb66a
URL:    
http://git.sip-router.org/cgi-bin/gitweb.cgi/sip-router/?a=commit;h=141808e9c0789e56f29297e2d2c185e091ebb66a

Author: Henning Westerholt <[email protected]>
Committer: Henning Westerholt <[email protected]>
Date:   Thu May  2 23:41:28 2013 +0200

memcached: port to more recent memory manager callback structure

* port to more recent memory manager callback structure
* add small wrapper for calloc, implemented not optimal at the moment
  because the pkg_calloc from core/mem is not exported yet
* add initial code to check for server connection during startup, not
  enabled yet as its work in progress
* reorder structure a bit to allow for clean shutdown because of internal mm

---

 modules/memcached/memcached.c |  110 ++++++++++++++++++++++++-----------------
 1 files changed, 65 insertions(+), 45 deletions(-)

diff --git a/modules/memcached/memcached.c b/modules/memcached/memcached.c
index c72ccf1..32852d9 100644
--- a/modules/memcached/memcached.c
+++ b/modules/memcached/memcached.c
@@ -107,7 +107,7 @@ struct module_exports exports = {
  * \param mem freed memory
  * \see pkg_free
  */
-static inline void mcd_free(void *mem) {
+static inline void mcd_free(memcached_st *ptr, void *mem, void *context) {
        pkg_free(mem);
 }
 
@@ -118,7 +118,7 @@ static inline void mcd_free(void *mem) {
  * \return allocated memory, or NULL on failure
  * \see pkg_malloc
  */
-static inline void* mcd_malloc(const size_t size) {
+static inline void* mcd_malloc(memcached_st *ptr, const size_t size, void 
*context) {
        return pkg_malloc(size);
 }
 
@@ -130,10 +130,43 @@ static inline void* mcd_malloc(const size_t size) {
  * \return allocated memory, or NULL on failure
  * \see pkg_realloc
  */
-static inline void* mcd_realloc(void *mem, const size_t size) {
+static inline void* mcd_realloc(memcached_st *ptr, void *mem, const size_t 
size, void *context) {
        return pkg_realloc(mem, size);
 }
 
+
+/*!
+ * \brief Wrapper functions around our internal memory management
+ * \param mem pointer to allocated memory
+ * \param size new size of memory area
+ * \return allocated memory, or NULL on failure
+ * \see pkg_malloc
+ * \todo this is not optimal,  use internal calloc implemention which is not 
exported yet
+ */
+static inline void * mcd_calloc(memcached_st *ptr, size_t nelem, const size_t 
elsize, void *context) {
+       void* tmp = NULL;
+       tmp = pkg_malloc(nelem * elsize);
+       if (tmp != NULL) {
+               memset(tmp, 0, nelem * elsize);
+       }
+       return tmp;
+}
+
+/**
+ * \brief Callback to check if we could connect successfully to a server
+ * \param ptr memcached handler
+ * \param server server instance
+ * \param context context for callback
+ * \return MEMCACHED_SUCCESS on success, MEMCACHED_CONNECTION_FAILURE on 
failure
+ * \todo FIXME
+static inline memcached_server_fn mcd_check_connection(const memcached_st 
*ptr, memcached_server_instance_st my_server, void *context) {
+       if (my_server->fd < 0) {
+               return MEMCACHED_CONNECTION_FAILURE;
+       }
+       return MEMCACHED_SUCCESS;
+}
+*/
+
 /*!
  * \brief Module initialization function
  * \return 0 on success, -1 on failure
@@ -161,54 +194,25 @@ static int mod_init(void) {
        strncpy(server, mcd_srv_str, len);
        server[len] = '\0';
 
-        servers = memcached_server_list_append(servers, server, atoi(port), 
&rc);
-
        memcached_h = memcached_create(NULL);
        if (memcached_h == NULL) {
                LM_ERR("could not create memcached structure\n");
                return -1;
        }
        LM_DBG("allocated new server handle at %p", memcached_h);
-       
-       #ifdef MEMCACHED_ENABLE_DEPRECATED
-       /** 
-        * \note Set callbacks to our internal memory manager
-        * \bug this don't work for now
-        * \todo Move to new memcached_set_memory_allocators function, this 
deprecated since 0.32
-        * 
-        * MEMCACHED_CALLBACK_MALLOC_FUNCTION
-        * This alllows yout to pass in a customized version of malloc that
-        * will be used instead of the builtin malloc(3) call. The prototype
-        * for this is:
-        * void *(*memcached_malloc_function)(memcached_st *ptr, const size_t 
size);
-        * 
-        * MEMCACHED_CALLBACK_REALLOC_FUNCTION
-        * This alllows yout to pass in a customized version of realloc that
-        * will be used instead of the builtin realloc(3) call. The prototype
-        * for this is:
-        * void *(*memcached_realloc_function)(memcached_st *ptr, void *mem, 
const size_t size);
-        * 
-        * MEMCACHED_CALLBACK_FREE_FUNCTION
-        * This alllows yout to pass in a customized version of realloc that
-        * will be used instead of the builtin free(3) call. The prototype
-        * for this is:
-        * typedef void (*memcached_free_function)(memcached_st *ptr, void 
*mem);
-        */
-       LM_DBG("set memory manager callbacks"); 
-       if (memcached_callback_set(memcached_h, 
MEMCACHED_CALLBACK_MALLOC_FUNCTION, mcd_free) != MEMCACHED_SUCCESS) {
-               LM_ERR("could not set malloc callback handler");
-               return -1;
-       }
-       if (memcached_callback_set(memcached_h, 
MEMCACHED_CALLBACK_REALLOC_FUNCTION, mcd_realloc) != MEMCACHED_SUCCESS) {
-               LM_ERR("could not set realloc callback handler");
-               return -1;
-       }
-       if (memcached_callback_set(memcached_h, 
MEMCACHED_CALLBACK_FREE_FUNCTION, mcd_free) != MEMCACHED_SUCCESS) {
-               LM_ERR("could not set free callback handler");
+
+       LM_DBG("set memory manager callbacks");
+       rc = memcached_set_memory_allocators(memcached_h, 
(memcached_malloc_fn)mcd_malloc,
+                                            (memcached_free_fn)mcd_free, 
(memcached_realloc_fn)mcd_realloc,
+                                            (memcached_calloc_fn)mcd_calloc, 
NULL);
+       if (rc == MEMCACHED_SUCCESS) {
+               LM_DBG("memory manager callbacks set");
+       } else {
+               LM_ERR("memory manager callbacks not set, returned %s.\n", 
memcached_strerror(memcached_h, rc));
                return -1;
        }
-       LM_DBG("memory manager callbacks set");
-       #endif
+       
+        servers = memcached_server_list_append(servers, server, atoi(port), 
&rc);
        
        if (memcached_behavior_set(memcached_h, 
MEMCACHED_BEHAVIOR_CONNECT_TIMEOUT, mcd_timeout) != MEMCACHED_SUCCESS) {
                LM_ERR("could not set server connection timeout");
@@ -223,6 +227,10 @@ static int mod_init(void) {
        }
 
        pkg_free(server);
+
+       /** \todo FIXME logic to handle connection errors on startup
+       memcached_server_cursor(memcached_h, (const memcached_server_fn*) 
&mcd_check_connection, NULL, 1);
+       */
        
        LM_INFO("libmemcached version is %s\n", memcached_lib_version());
        return 0;
@@ -233,8 +241,20 @@ static int mod_init(void) {
  * \brief Module shutdown function
  */
 static void mod_destroy(void) {
-       if (memcached_h != NULL)
-               memcached_free(memcached_h);
+       memcached_return rc;
+       
        if (servers != NULL)
                memcached_server_list_free(servers);
+       
+       /* unset custom memory manager to enable clean shutdown of in system 
memory allocated server structure */
+       LM_DBG("remove memory manager callbacks");
+       rc = memcached_set_memory_allocators(memcached_h, NULL, NULL, NULL, 
NULL, NULL);
+       if (rc == MEMCACHED_SUCCESS) {
+               LM_DBG("memory manager callbacks removed");
+       } else {
+               LM_ERR("memory manager callbacks not removed, returned %s but 
continue anyway.\n", memcached_strerror(memcached_h, rc));
+       }
+       
+       if (memcached_h != NULL)
+               memcached_free(memcached_h);
 }


_______________________________________________
sr-dev mailing list
[email protected]
http://lists.sip-router.org/cgi-bin/mailman/listinfo/sr-dev

Reply via email to