Hi,

The patch allows reusing resource containers.
Although the existing code calls free_container when the
extra resources are destroyed, this container is never used.
Patch adds extra list that maintains those resources, and
uses them instead allocating the new one over and over again.

The second patch adds the two new api function for obtaining
private reslist members. Since I'm using the reslist inside
proxy balancer I have to maintain an extra mutex protected
variable that actually holds the number of free resources present
and maintained inside reslist. Being able to obtain that private
member helps selecting the resource list with highest number of
idle resources as well as list that wouldn't block on acquire.


Regards, MT.
Index: apr_reslist.h
===================================================================
RCS file: /home/cvspublic/apr-util/include/apr_reslist.h,v
retrieving revision 1.9
diff -u -r1.9 apr_reslist.h
--- apr_reslist.h       15 Mar 2004 08:21:26 -0000      1.9
+++ apr_reslist.h       8 Sep 2004 08:16:32 -0000
@@ -131,6 +131,20 @@
 APU_DECLARE(apr_status_t) apr_reslist_invalidate(apr_reslist_t *reslist,
                                                  void *resource);
 
+/**
+ * Get the number of idle resources.
+ * @param reslist The resource list.
+ * Return a number if idle resources.
+ */
+APU_DECLARE(int) apr_reslist_idle_get(apr_reslist_t *reslist);
+
+/**
+ * Get the number of resources that can be acquired
+ * withouth the need to wait for a free resource.
+ * @param reslist The resource list.
+ * Return a number acquirable resources.
+ */
+APU_DECLARE(int) apr_reslist_acquirable_get(apr_reslist_t *reslist);
 
 #ifdef __cplusplus
 }

Index: apr_reslist.c
===================================================================
RCS file: /home/cvspublic/apr-util/misc/apr_reslist.c,v
retrieving revision 1.9
diff -u -r1.9 apr_reslist.c
--- apr_reslist.c       15 Mar 2004 08:21:26 -0000      1.9
+++ apr_reslist.c       13 Sep 2004 12:53:52 -0000
@@ -55,6 +55,7 @@
     void *params; /* opaque data passed to constructor and destructor calls */
     apr_resring_t avail_list;
     apr_resring_t free_list;
+    apr_resring_t maint_list;
     apr_thread_mutex_t *listlock;
     apr_thread_cond_t *avail;
 };
@@ -116,8 +117,13 @@
     apr_status_t rv;
     apr_res_t *res;
 
-    res = apr_pcalloc(reslist->pool, sizeof(*res));
-
+    if (APR_RING_EMPTY(&reslist->maint_list, apr_res_t, link)) {
+        res = apr_pcalloc(reslist->pool, sizeof(*res));
+    }
+    else {
+        res = APR_RING_FIRST(&reslist->maint_list);
+        APR_RING_REMOVE(res, link);
+    }
     rv = reslist->constructor(&res->opaque, reslist->params, reslist->pool);
 
     *ret_res = res;
@@ -219,7 +225,7 @@
             apr_thread_mutex_unlock(reslist->listlock);
             return rv;
         }
-        free_container(reslist, res);
+        APR_RING_INSERT_TAIL(&reslist->maint_list, res, apr_res_t, link);
     }
 
     apr_thread_mutex_unlock(reslist->listlock);
@@ -255,6 +261,7 @@
 
     APR_RING_INIT(&rl->avail_list, apr_res_t, link);
     APR_RING_INIT(&rl->free_list, apr_res_t, link);
+    APR_RING_INIT(&rl->maint_list, apr_res_t, link);
 
     rv = apr_thread_mutex_create(&rl->listlock, APR_THREAD_MUTEX_DEFAULT,
                                  pool);
@@ -369,6 +376,16 @@
     reslist->ntotal--;
     apr_thread_mutex_unlock(reslist->listlock);
     return ret;
+}
+
+APU_DECLARE(int) apr_reslist_idle_get(apr_reslist_t *reslist)
+{
+    return reslist->nidle;
+}
+
+APU_DECLARE(int) apr_reslist_acquirable_get(apr_reslist_t *reslist)
+{
+    return (reslist->hmax - reslist->ntotal);
 }
 
 #endif  /* APR_HAS_THREADS */


Index: apr_reslist.c
===================================================================
RCS file: /home/cvspublic/apr-util/misc/apr_reslist.c,v
retrieving revision 1.9
diff -u -r1.9 apr_reslist.c
--- apr_reslist.c       15 Mar 2004 08:21:26 -0000      1.9
+++ apr_reslist.c       13 Sep 2004 12:54:26 -0000
@@ -55,6 +55,7 @@
     void *params; /* opaque data passed to constructor and destructor calls */
     apr_resring_t avail_list;
     apr_resring_t free_list;
+    apr_resring_t maint_list;
     apr_thread_mutex_t *listlock;
     apr_thread_cond_t *avail;
 };
@@ -116,8 +117,13 @@
     apr_status_t rv;
     apr_res_t *res;
 
-    res = apr_pcalloc(reslist->pool, sizeof(*res));
-
+    if (APR_RING_EMPTY(&reslist->maint_list, apr_res_t, link)) {
+        res = apr_pcalloc(reslist->pool, sizeof(*res));
+    }
+    else {
+        res = APR_RING_FIRST(&reslist->maint_list);
+        APR_RING_REMOVE(res, link);
+    }
     rv = reslist->constructor(&res->opaque, reslist->params, reslist->pool);
 
     *ret_res = res;
@@ -219,7 +225,7 @@
             apr_thread_mutex_unlock(reslist->listlock);
             return rv;
         }
-        free_container(reslist, res);
+        APR_RING_INSERT_TAIL(&reslist->maint_list, res, apr_res_t, link);
     }
 
     apr_thread_mutex_unlock(reslist->listlock);
@@ -255,6 +261,7 @@
 
     APR_RING_INIT(&rl->avail_list, apr_res_t, link);
     APR_RING_INIT(&rl->free_list, apr_res_t, link);
+    APR_RING_INIT(&rl->maint_list, apr_res_t, link);
 
     rv = apr_thread_mutex_create(&rl->listlock, APR_THREAD_MUTEX_DEFAULT,
                                  pool);

Attachment: smime.p7s
Description: S/MIME Cryptographic Signature

Reply via email to