summaryrefslogtreecommitdiffstats
path: root/libglusterfs/src/mem-pool.c
diff options
context:
space:
mode:
Diffstat (limited to 'libglusterfs/src/mem-pool.c')
-rw-r--r--libglusterfs/src/mem-pool.c42
1 files changed, 31 insertions, 11 deletions
diff --git a/libglusterfs/src/mem-pool.c b/libglusterfs/src/mem-pool.c
index 5fdd5e5f2..f3dfc2149 100644
--- a/libglusterfs/src/mem-pool.c
+++ b/libglusterfs/src/mem-pool.c
@@ -24,10 +24,12 @@
#include <stdarg.h>
#define GF_MEM_POOL_LIST_BOUNDARY (sizeof(struct list_head))
-#define GF_MEM_POOL_PAD_BOUNDARY (GF_MEM_POOL_LIST_BOUNDARY + sizeof(int))
+#define GF_MEM_POOL_PTR (sizeof(struct mem_pool*))
+#define GF_MEM_POOL_PAD_BOUNDARY (GF_MEM_POOL_LIST_BOUNDARY + GF_MEM_POOL_PTR + sizeof(int))
#define mem_pool_chunkhead2ptr(head) ((head) + GF_MEM_POOL_PAD_BOUNDARY)
#define mem_pool_ptr2chunkhead(ptr) ((ptr) - GF_MEM_POOL_PAD_BOUNDARY)
#define is_mem_chunk_in_use(ptr) (*ptr == 1)
+#define mem_pool_from_ptr(ptr) ((ptr) + GF_MEM_POOL_LIST_BOUNDARY)
#define GF_MEM_HEADER_SIZE (4 + sizeof (size_t) + sizeof (xlator_t *) + 4 + 8)
#define GF_MEM_TRAILER_SIZE 8
@@ -379,6 +381,7 @@ mem_get (struct mem_pool *mem_pool)
struct list_head *list = NULL;
void *ptr = NULL;
int *in_use = NULL;
+ struct mem_pool **pool_ptr = NULL;
if (!mem_pool) {
gf_log ("mem-pool", GF_LOG_ERROR, "invalid argument");
@@ -395,7 +398,8 @@ mem_get (struct mem_pool *mem_pool)
mem_pool->cold_count--;
ptr = list;
- in_use = (ptr + GF_MEM_POOL_LIST_BOUNDARY);
+ in_use = (ptr + GF_MEM_POOL_LIST_BOUNDARY +
+ GF_MEM_POOL_PTR);
*in_use = 1;
goto fwd_addr_out;
@@ -421,17 +425,20 @@ mem_get (struct mem_pool *mem_pool)
* because it is too much work knowing that a better slab
* allocator is coming RSN.
*/
- ptr = MALLOC (mem_pool->real_sizeof_type);
+ ptr = GF_CALLOC (1, mem_pool->padded_sizeof_type,
+ gf_common_mt_mem_pool);
+ gf_log_callingfn ("mem-pool", GF_LOG_DEBUG, "Mem pool is full. "
+ "Callocing mem");
/* Memory coming from the heap need not be transformed from a
* chunkhead to a usable pointer since it is not coming from
* the pool.
*/
- goto unlocked_out;
}
fwd_addr_out:
+ pool_ptr = mem_pool_from_ptr (ptr);
+ *pool_ptr = (struct mem_pool *)mem_pool;
ptr = mem_pool_chunkhead2ptr (ptr);
-unlocked_out:
UNLOCK (&mem_pool->lock);
return ptr;
@@ -458,25 +465,39 @@ __is_member (struct mem_pool *pool, void *ptr)
void
-mem_put (struct mem_pool *pool, void *ptr)
+mem_put (void *ptr)
{
struct list_head *list = NULL;
int *in_use = NULL;
void *head = NULL;
+ struct mem_pool **tmp = NULL;
+ struct mem_pool *pool = NULL;
- if (!pool || !ptr) {
+ if (!ptr) {
gf_log ("mem-pool", GF_LOG_ERROR, "invalid argument");
return;
}
+ list = head = mem_pool_ptr2chunkhead (ptr);
+ tmp = mem_pool_from_ptr (head);
+ if (!tmp) {
+ gf_log ("mem-pool", GF_LOG_ERROR, "ptr header is corrupted");
+ return;
+ }
+
+ pool = *tmp;
+ if (!pool) {
+ gf_log ("mem-pool", GF_LOG_ERROR, "mem-pool ptr is NULL");
+ return;
+ }
LOCK (&pool->lock);
{
switch (__is_member (pool, ptr))
{
case 1:
- list = head = mem_pool_ptr2chunkhead (ptr);
- in_use = (head + GF_MEM_POOL_LIST_BOUNDARY);
+ in_use = (head + GF_MEM_POOL_LIST_BOUNDARY +
+ GF_MEM_POOL_PTR);
if (!is_mem_chunk_in_use(in_use)) {
gf_log_callingfn ("mem-pool", GF_LOG_CRITICAL,
"mem_put called on freed ptr %p of mem "
@@ -506,7 +527,7 @@ mem_put (struct mem_pool *pool, void *ptr)
* not have enough info to distinguish between the two
* situations.
*/
- FREE (ptr);
+ GF_FREE (list);
break;
default:
/* log error */
@@ -516,7 +537,6 @@ mem_put (struct mem_pool *pool, void *ptr)
UNLOCK (&pool->lock);
}
-
void
mem_pool_destroy (struct mem_pool *pool)
{