summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorRaghavendra G <raghavendra@gluster.com>2009-10-28 04:46:25 +0000
committerAnand V. Avati <avati@dev.gluster.com>2009-10-29 10:07:49 -0700
commit14962ce3e69e452a2447c12cde3369759365fda9 (patch)
tree19702c29142c35e05a1548f9471c77f6a4eab05e
parent13e6947744e8a26d2380af200942fd4ed61fd845 (diff)
performance/io-cache: change the hash function used for rbtree based hash table.
- the earlier hash function does not distribute pages uniformly for offsets that fit into 32 bits. The reason is that the hash function just xors the contents of the key 4 bytes at a time with the current value of hash. Hence for keys that fit into 32 bits, the hash will be the key itself. Since we are using the rounded_offset (which is a multiple of 128KB) as the key, the key will be exactly divisible by the number of buckets configured (4096) resolving all the pages into the first bucket. Signed-off-by: Anand V. Avati <avati@dev.gluster.com> BUG: 335 (Io-cache optimization) URL: http://bugs.gluster.com/cgi-bin/bugzilla3/show_bug.cgi?id=335
-rw-r--r--libglusterfs/src/common-utils.c15
-rw-r--r--libglusterfs/src/common-utils.h1
-rw-r--r--xlators/performance/io-cache/src/io-cache.c16
-rw-r--r--xlators/performance/io-cache/src/ioc-inode.c12
4 files changed, 32 insertions, 12 deletions
diff --git a/libglusterfs/src/common-utils.c b/libglusterfs/src/common-utils.c
index de0cb774b..3f52a90a0 100644
--- a/libglusterfs/src/common-utils.c
+++ b/libglusterfs/src/common-utils.c
@@ -56,6 +56,21 @@ struct dnscache6 {
struct addrinfo *next;
};
+
+int
+gf_log2 (unsigned long x)
+{
+ int val = 0;
+
+ while (x != 1) {
+ x /= 2;
+ val++;
+ }
+
+ return val;
+}
+
+
int32_t
gf_resolve_ip6 (const char *hostname,
uint16_t port,
diff --git a/libglusterfs/src/common-utils.h b/libglusterfs/src/common-utils.h
index c5869f4a4..48788d295 100644
--- a/libglusterfs/src/common-utils.h
+++ b/libglusterfs/src/common-utils.h
@@ -330,6 +330,7 @@ int gf_lockfd (int fd);
int gf_unlockfd (int fd);
int get_checksum_for_file (int fd, uint32_t *checksum);
+int gf_log2 (unsigned long x);
#endif /* _COMMON_UTILS_H */
diff --git a/xlators/performance/io-cache/src/io-cache.c b/xlators/performance/io-cache/src/io-cache.c
index 5c1f74db1..da3f4f15d 100644
--- a/xlators/performance/io-cache/src/io-cache.c
+++ b/xlators/performance/io-cache/src/io-cache.c
@@ -30,6 +30,8 @@
#include <assert.h>
#include <sys/time.h>
+extern int ioc_log2_page_size;
+
uint32_t
ioc_get_priority (ioc_table_t *table, const char *path);
@@ -1234,11 +1236,12 @@ out:
int32_t
init (xlator_t *this)
{
- ioc_table_t *table = NULL;
- dict_t *options = this->options;
- uint32_t index = 0;
- char *cache_size_string = NULL;
- int32_t ret = -1;
+ ioc_table_t *table = NULL;
+ dict_t *options = this->options;
+ uint32_t index = 0;
+ char *cache_size_string = NULL;
+ int32_t ret = -1;
+ glusterfs_ctx_t *ctx = NULL;
if (!this->children || this->children->next) {
gf_log (this->name, GF_LOG_ERROR,
@@ -1320,6 +1323,9 @@ init (xlator_t *this)
this->private = table;
ret = 0;
+ ctx = this->ctx;
+ ioc_log2_page_size = gf_log2 (ctx->page_size);
+
out:
if (ret == -1) {
if (table != NULL) {
diff --git a/xlators/performance/io-cache/src/ioc-inode.c b/xlators/performance/io-cache/src/ioc-inode.c
index e647b3183..11da86312 100644
--- a/xlators/performance/io-cache/src/ioc-inode.c
+++ b/xlators/performance/io-cache/src/ioc-inode.c
@@ -24,18 +24,16 @@
#include "io-cache.h"
+int ioc_log2_page_size;
inline uint32_t
ioc_hashfn (void *data, int len)
{
- uint32_t hash = 0;
- while (len > 0) {
- hash ^= *(uint32_t *)data;
- data += sizeof (uint32_t);
- len -= sizeof (uint32_t);
- }
+ off_t offset;
+
+ offset = *(off_t *) data;
- return hash;
+ return (offset >> ioc_log2_page_size);
}
/*