all: $(TOP_INCDIR)/afs/opr.h \
$(TOP_INCDIR)/afs/opr_assert.h \
+ $(TOP_INCDIR)/opr/jhash.h \
$(TOP_INCDIR)/opr/queue.h \
$(TOP_INCDIR)/opr/rbtree.h \
$(TOP_LIBDIR)/libopr.a
$(TOP_INCDIR)/afs/opr_assert.h: opr_assert.h
$(INSTALL_DATA) opr_assert.h $@
+$(TOP_INCDIR)/opr/jhash.h: jhash.h
+ $(INSTALL_DATA) jhash.h $@
+
$(TOP_INCDIR)/opr/queue.h: queue.h
$(INSTALL_DATA) queue.h $@
INCFILES = \
$(INCFILEDIR)\opr.h \
$(INCFILEDIR)\opr_assert.h \
+ $(DESTDIR)\include\opr\jhash.h \
$(DESTDIR)\include\opr\queue.h \
$(DESTDIR)\include\opr\rbtree.h
--- /dev/null
+/*
+ * Copyright (c) 2006 Bob Jenkins
+ * Copyright (c) 2011 Your File System Inc.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR `AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+/* This is an OPR version of Bob Jenkins' hash routines. His original copyright
+ * declaration reads:
+ *
+ * lookup3.c, by Bob Jenkins, May 2006, Public Domain.
+ *
+ * You can use this free for any purpose. It's in the public domain.
+ * It has no warranty.
+ */
+
+#ifndef OPENAFS_OPR_JHASH_H
+#define OPENAFS_OPR_JHASH_H 1
+
+#define opr_jhash_size(n) ((uint32_t)1<<(n))
+#define opr_jhash_mask(n) (opr_jhash_size(n)-1)
+#define opr_jhash_rot(x,k) (((x)<<(k)) | ((x)>>(32-(k))))
+
+#define opr_jhash_mix(a,b,c) \
+{ \
+ a -= c; a ^= opr_jhash_rot(c, 4); c += b; \
+ b -= a; b ^= opr_jhash_rot(a, 6); a += c; \
+ c -= b; c ^= opr_jhash_rot(b, 8); b += a; \
+ a -= c; a ^= opr_jhash_rot(c,16); c += b; \
+ b -= a; b ^= opr_jhash_rot(a,19); a += c; \
+ c -= b; c ^= opr_jhash_rot(b, 4); b += a; \
+}
+
+#define opr_jhash_final(a,b,c) \
+{ \
+ c ^= b; c -= opr_jhash_rot(b,14); \
+ a ^= c; a -= opr_jhash_rot(c,11); \
+ b ^= a; b -= opr_jhash_rot(a,25); \
+ c ^= b; c -= opr_jhash_rot(b,16); \
+ a ^= c; a -= opr_jhash_rot(c,4); \
+ b ^= a; b -= opr_jhash_rot(a,14); \
+ c ^= b; c -= opr_jhash_rot(b,24); \
+}
+
+static_inline uint32_t
+opr_jhash(const uint32_t *k, size_t length, uint32_t initval)
+{
+ uint32_t a,b,c;
+
+ /* Set up the internal state */
+ a = b = c = 0xdeadbeef + (((uint32_t)length)<<2) + initval;
+
+ while (length > 3) {
+ a += k[0];
+ b += k[1];
+ c += k[2];
+ opr_jhash_mix(a, b, c);
+ length -= 3;
+ k += 3;
+ }
+
+ /* All the case statements fall through */
+ switch(length) {
+ case 3 : c+=k[2];
+ case 2 : b+=k[1];
+ case 1 : a+=k[0];
+ opr_jhash_final(a, b, c);
+ case 0: /* case 0: nothing left to add */
+ break;
+ }
+
+ return c;
+}
+
+/* Simplified version of the above function to hash just one int */
+
+static_inline uint32_t
+opr_jhash_int(uint32_t a, uint32_t initval) {
+ uint32_t b, c;
+
+ a += 0xdeadbeef + 4 + initval;
+ b = c = 0xdeadbeef + 4 + initval;
+ opr_jhash_final(a, b, c);
+
+ return c;
+}
+
+#endif
auth/superuser
auth/authcon
cmd/command
+opr/jhash
opr/queues
opr/rbtree
ptserver/pt_util
# git ls-files -i --exclude-standard
# to check that you haven't inadvertently ignored any tracked files.
+/jhash-t
/rbtree-t
LIBS=../tap/libtap.a $(abs_top_builddir)/lib/libopr.a
-tests = queues-t rbtree-t
+tests = jhash-t queues-t rbtree-t
all check test tests: $(tests)
rbtree-t: rbtree-t.o $(LIBS)
$(AFS_LDRULE) rbtree-t.o ../tap/libtap.a $(LIBS) $(XLIBS)
+jhash-t: jhash-t.o
+ $(AFS_LDRULE) jhash-t.o ../tap/libtap.a $(XLIBS)
+
clean distclean:
$(RM) -f $(tests) *.o core
--- /dev/null
+/*
+ * Copyright (c) 2011 Your File System Inc.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR `AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include <afsconfig.h>
+#include <afs/param.h>
+
+#include <roken.h>
+#include <tap/basic.h>
+
+#include <opr/jhash.h>
+
+/* Bob Jenkins' lookup3.c comes with a load of self test functions, but
+ * unfortunately, they all use 'hashlittle' (his unaligned hash function). As
+ * we have only got 'hashword' (word aligned arrays) in OpenAFS, we need to roll
+ * our own tests.
+ */
+
+int
+main(int argc, char **argv)
+{
+ plan(8);
+ uint32_t test[] = {3526055646, 2064483663, 3234460805, 3963629775};
+
+ is_int(256, opr_jhash_size(8), "opr_jhash_size returns expected value");
+ is_int(255, opr_jhash_mask(8), "opr_jhash_mask returns expected value");
+
+ is_int(0xdeadbeef, opr_jhash(test, 0, 0), "empty array hashes as expected");
+ is_int(766530906, opr_jhash(test, 4, 0), "simple array works");
+ is_int(3782684773, opr_jhash(test, 4, 1), "changing initval works");
+
+ test[2]++;
+ is_int(1977082159, opr_jhash(test, 4, 0), "modifying value works");
+
+ is_int(1100796964, opr_jhash(test, 1, 0),
+ "single value works through jhash");
+ is_int(1100796964, opr_jhash_int(test[0], 0),
+ "single value works through jhash_int");
+
+ return 0;
+}