#include <errno.h>
#include <signal.h>
+#include <urcu/tls-compat.h>
+
#ifdef __linux__
#include <syscall.h>
#endif
unsigned long remove;
};
-extern unsigned int __thread rand_lookup;
-extern unsigned long __thread nr_add;
-extern unsigned long __thread nr_addexist;
-extern unsigned long __thread nr_del;
-extern unsigned long __thread nr_delnoent;
-extern unsigned long __thread lookup_fail;
-extern unsigned long __thread lookup_ok;
+extern DECLARE_URCU_TLS(unsigned int, rand_lookup);
+extern DECLARE_URCU_TLS(unsigned long, nr_add);
+extern DECLARE_URCU_TLS(unsigned long, nr_addexist);
+extern DECLARE_URCU_TLS(unsigned long, nr_del);
+extern DECLARE_URCU_TLS(unsigned long, nr_delnoent);
+extern DECLARE_URCU_TLS(unsigned long, lookup_fail);
+extern DECLARE_URCU_TLS(unsigned long, lookup_ok);
extern struct cds_lfht *test_ht;
write_pool_size;
extern int validate_lookup;
+extern unsigned long nr_hash_chains;
+
extern int count_pipe[2];
static inline void loop_sleep(unsigned long l)
void set_affinity(void);
-/* rw test */
-void test_hash_rw_sigusr1_handler(int signo);
-void test_hash_rw_sigusr2_handler(int signo);
-void *test_hash_rw_thr_reader(void *_count);
-void *test_hash_rw_thr_writer(void *_count);
-
/*
* returns 0 if test should end.
*/
return !test_stop;
}
-extern unsigned long long __thread nr_writes;
-extern unsigned long long __thread nr_reads;
+extern DECLARE_URCU_TLS(unsigned long long, nr_writes);
+extern DECLARE_URCU_TLS(unsigned long long, nr_reads);
extern unsigned int nr_readers;
extern unsigned int nr_writers;
#if (CAA_BITS_PER_LONG == 32)
static inline
-unsigned long test_hash(const void *_key, size_t length, unsigned long seed)
+unsigned long test_hash_mix(const void *_key, size_t length, unsigned long seed)
{
unsigned int key = (unsigned int) _key;
}
#else
static inline
-unsigned long test_hash(const void *_key, size_t length, unsigned long seed)
+unsigned long test_hash_mix(const void *_key, size_t length, unsigned long seed)
{
union {
uint64_t v64;
}
#endif
+/*
+ * Hash function with nr_hash_chains != 0 for testing purpose only!
+ * Creates very long hash chains, deteriorating the hash table into a
+ * few linked lists, depending on the nr_hash_chains value. The purpose
+ * of this test is to check how the hash table behaves with hash chains
+ * containing different values, which is a rare case in a normal hash
+ * table.
+ */
+static inline
+unsigned long test_hash(const void *_key, size_t length,
+ unsigned long seed)
+{
+ if (nr_hash_chains == 0) {
+ return test_hash_mix(_key, length, seed);
+ } else {
+ unsigned long v;
+
+ assert(length == sizeof(unsigned long));
+ v = (unsigned long) _key;
+ return v % nr_hash_chains;
+ }
+}
+
unsigned long test_compare(const void *key1, size_t key1_len,
const void *key2, size_t key2_len);
void free_node_cb(struct rcu_head *head);
+/* rw test */
+void test_hash_rw_sigusr1_handler(int signo);
+void test_hash_rw_sigusr2_handler(int signo);
+void *test_hash_rw_thr_reader(void *_count);
+void *test_hash_rw_thr_writer(void *_count);
+int test_hash_rw_populate_hash(void);
+
+/* unique test */
+void test_hash_unique_sigusr1_handler(int signo);
+void test_hash_unique_sigusr2_handler(int signo);
+void *test_hash_unique_thr_reader(void *_count);
+void *test_hash_unique_thr_writer(void *_count);
+int test_hash_unique_populate_hash(void);
+
#endif /* _TEST_URCU_HASH_H */