]> mj.ucw.cz Git - libucw.git/blobdiff - ucw/hashtable.h
Resources: Allow res_free(NULL) and res_detach(NULL)
[libucw.git] / ucw / hashtable.h
index 364ee255cdc2511fa3786564855b6dd6295898c2..622f071aa7a663151ab79bc5d3fee36d6268b7cb 100644 (file)
@@ -3,6 +3,7 @@
  *
  *     (c) 2002--2004 Martin Mares <mj@ucw.cz>
  *     (c) 2002--2005 Robert Spalek <robert@ucw.cz>
+ *     (c) 2010 Pavel Charvat <pchar@ucw.cz>
  *
  *     This software may be freely distributed and used according to the terms
  *     of the GNU Lesser General Public License.
  *                     will leak pool memory.
  *  HASH_AUTO_POOL=size        Create a pool of the given block size automatically.
  *  HASH_USE_ELTPOOL=pool Allocate all nodes from given eltpool.
- *                     Only works for nodes of limited size.
  *  HASH_AUTO_ELTPOOL=count Create an eltpool of the given number of elements in each chunk.
- *                     Only works for fixed-sized nodes and zero HASH_GIVE_EXTRA_SIZE.
  *  HASH_ZERO_FILL     New entries should be initialized to all zeroes.
  *  HASH_TABLE_ALLOC   The hash table itself will be allocated and freed using
  *                     the same allocation functions as the nodes instead of
  *                     the default xmalloc().
- *  HASH_TABLE_GROW    Never decrease the size of the hash table itself
+ *  HASH_TABLE_GROWING Never decrease the size of the hash table itself
  *  HASH_TABLE_DYNAMIC Support multiple hash tables; the first parameter of all
  *                     hash table operations is struct HASH_PREFIX(table) *.
  *  HASH_TABLE_VARS    Extra variables to be defined in table structure
@@ -162,6 +161,9 @@ typedef struct P(bucket) {
 } P(bucket);
 
 struct P(table) {
+#ifdef HASH_TABLE_VARS
+  HASH_TABLE_VARS
+#endif
   uns hash_size;
   uns hash_count, hash_max, hash_min, hash_hard_max;
   P(bucket) **ht;
@@ -171,9 +173,6 @@ struct P(table) {
 #ifdef HASH_AUTO_ELTPOOL
   struct eltpool *eltpool;
 #endif
-#ifdef HASH_TABLE_VARS
-  HASH_TABLE_VARS
-#endif
 };
 
 #ifdef HASH_TABLE_DYNAMIC
@@ -359,16 +358,13 @@ static inline void P(cleanup_alloc) (TAU) { mp_delete(T.pool); }
 #elif defined(HASH_USE_ELTPOOL)
 /* If the caller has requested to use his eltpool, do so */
 #include "ucw/eltpool.h"
-static inline void * P(alloc) (TAUC unsigned int size) { ASSERT(size <= (HASH_USE_ELTPOOL)->elt_size); return ep_alloc(HASH_USE_ELTPOOL); }
+static inline void * P(alloc) (TAUC unsigned int size UNUSED) { ASSERT(size <= (HASH_USE_ELTPOOL)->elt_size); return ep_alloc(HASH_USE_ELTPOOL); }
 static inline void P(free) (TAUC void *x) { ep_free(HASH_USE_ELTPOOL, x); }
 static inline void P(init_alloc) (TAU) { }
 static inline void P(cleanup_alloc) (TAU) { }
 
 #elif defined(HASH_AUTO_ELTPOOL)
 /* Use our own eltpools */
-#ifdef HASH_GIVE_EXTRA_SIZE
-#error HASH_AUTO_ELTPOOL not supported in combination with variable-sized nodes
-#endif
 #include "ucw/eltpool.h"
 static inline void * P(alloc) (TAUC unsigned int size UNUSED) { return ep_alloc(T.eltpool); }
 static inline void P(free) (TAUC void *x) { ep_free(T.eltpool, x); }
@@ -385,6 +381,10 @@ static inline void P(cleanup_alloc) (TAU) { }
 
 #endif
 
+#if defined(HASH_USE_ELTPOOL) && defined(HASH_GIVE_EXTRA_SIZE)
+#error Eltpools not supported in combination with variable-sized nodes
+#endif
+
 #ifdef HASH_GIVE_TABLE_ALLOC
 /* If the caller has requested to use his own allocation functions, do so */
 #elif defined(HASH_TABLE_ALLOC)
@@ -398,8 +398,8 @@ static inline void * P(table_alloc) (TAUC unsigned int size) { return xmalloc(si
 static inline void P(table_free) (TAUC void *x) { xfree(x); }
 #endif
 
-#if defined(HASH_USE_POOL) && defined(HASH_TABLE_ALLOC) && !defined(HASH_TABLE_GROW)
-#define HASH_TABLE_GROW
+#if defined(HASH_USE_POOL) && defined(HASH_TABLE_ALLOC) && !defined(HASH_TABLE_GROWING)
+#define HASH_TABLE_GROWING
 #endif
 
 #ifndef HASH_DEFAULT_SIZE
@@ -432,7 +432,7 @@ static void P(alloc_table) (TAU)
     T.hash_max = 2*T.hash_size;
   else
     T.hash_max = ~0U;
-#ifndef HASH_TABLE_GROW
+#ifndef HASH_TABLE_GROWING
   if (T.hash_size/2 > HASH_DEFAULT_SIZE)
     T.hash_min = T.hash_size/4;
   else
@@ -655,8 +655,9 @@ static int HASH_PREFIX(delete)(TAC HASH_KEY_DECL)
        {
          *bb = b->next;
          P(free)(TTC b);
-#ifndef HASH_TABLE_GROW
-         if (--T.hash_count < T.hash_min)
+         T.hash_count--;
+#ifndef HASH_TABLE_GROWING
+         if (T.hash_count < T.hash_min)
            P(rehash)(TTC T.hash_size/2);
 #endif
          return 1;
@@ -686,8 +687,9 @@ static void HASH_PREFIX(remove)(TAC HASH_NODE *n)
   ASSERT(b);
   *bb = b->next;
   P(free)(TTC b);
-#ifndef HASH_TABLE_GROW
-  if (--T.hash_count < T.hash_min)
+  T.hash_count--;
+#ifndef HASH_TABLE_GROWING
+  if (T.hash_count < T.hash_min)
     P(rehash)(TTC T.hash_size/2);
 #endif
 }
@@ -758,7 +760,7 @@ do {                                                                                        \
 #undef HASH_WANT_NEW
 #undef HASH_WANT_REMOVE
 #undef HASH_TABLE_ALLOC
-#undef HASH_TABLE_GROW
+#undef HASH_TABLE_GROWING
 #undef HASH_TABLE_DYNAMIC
 #undef HASH_TABLE_VARS
 #undef HASH_ZERO_FILL