11/*
2- * rapidhash V2.1 - Very fast, high quality, platform-independent hashing algorithm.
2+ * rapidhash V2.2 - Very fast, high quality, platform-independent hashing algorithm.
33 * Copyright (C) 2025 Nicolas De Carli
44 *
55 * Based on 'wyhash', by Wang Yi <godspeed_china@yeah.net>
5757 # define RAPIDHASH_ALWAYS_INLINE inline
5858 #endif
5959
60-
6160 #ifdef __cplusplus
6261 # define RAPIDHASH_NOEXCEPT noexcept
6362 # define RAPIDHASH_CONSTEXPR constexpr
7877 * Small input speed macro, improves small input speed at the expense of sacrificing large input speed.
7978 *
8079 * RAPIDHASH_UNROLLED: Normal behavior, max large input speed.
81- * RAPIDHASH_COMPACT: Improved small input speed.
80+ * RAPIDHASH_COMPACT: Improved small input speed and reduced code size.
81+ *
82+ * RAPIDHASH_SUPER_COMPACT: Almost always decreases speed for sizes > 95, but will further reduce code size.
8283 */
84+ #ifdef RAPIDHASH_SUPER_COMPACT
85+ # ifndef RAPIDHASH_COMPACT
86+ # define RAPIDHASH_COMPACT
87+ # endif
88+ #endif
8389 #ifndef RAPIDHASH_COMPACT
8490 # define RAPIDHASH_UNROLLED
8591 # define RAPIDHASH_UNLIKELY_BULK (x ) _unlikely_(x)
92+ # define RAPIDHASH_LIKELY_BULK (x ) _likely_(x)
8693 #elif defined(RAPIDHASH_UNROLLED )
8794 # error "cannot define RAPIDHASH_COMPACT and RAPIDHASH_UNROLLED simultaneously."
8895 #else
8996 # define RAPIDHASH_UNLIKELY_BULK (x ) (x)
97+ # define RAPIDHASH_LIKELY_BULK (x ) (x)
9098 #endif
9199
92100 /*
230238 }
231239 #endif
232240
233- /*
234- * Reads and combines 3 bytes of input.
235- *
236- * @param p Buffer to read from.
237- * @param k Length of @p, in bytes.
238- *
239- * Always reads and combines 3 bytes from memory.
240- * Guarantees to read each buffer position at least once.
241- *
242- * Returns a 64-bit value containing all three bytes read.
243- */
244- RAPIDHASH_INLINE_CONSTEXPR uint64_t rapid_readSmall (const uint8_t * p , size_t k ) RAPIDHASH_NOEXCEPT { return (((uint64_t )p [0 ])<<56 )|(((uint64_t )p [k >>1 ])<<32 )|p [k - 1 ];}
245241 /*
246242 * rapidhash main function.
247243 *
@@ -268,11 +264,11 @@ RAPIDHASH_INLINE_CONSTEXPR uint64_t rapidhash_internal(const void *key, size_t l
268264 b = rapid_read32 (plast );
269265 }
270266 } else if (_likely_ (len > 0 )) {
271- a = rapid_readSmall ( p , len ) ;
272- b = 0 ;
267+ a = ((( uint64_t ) p [ 0 ])<< 56 )| p [ len - 1 ] ;
268+ b = p [ len >> 1 ] ;
273269 } else
274270 a = b = 0 ;
275- } else if (_likely_ ( len <= 64 ) ) {
271+ } else if (len <= 64 ) {
276272 seed = rapid_mix (rapid_read64 (p ) ^ secret [0 ], rapid_read64 (p + 8 ) ^ seed );
277273 if (len > 32 ) {
278274 seed = rapid_mix (rapid_read64 (p + 16 ) ^ secret [1 ], rapid_read64 (p + 24 ) ^ seed );
@@ -329,6 +325,7 @@ RAPIDHASH_INLINE_CONSTEXPR uint64_t rapidhash_internal(const void *key, size_t l
329325 i -= 112 ;
330326 }
331327#endif
328+ #ifndef RAPIDHASH_SUPER_COMPACT
332329 if (_likely_ (i >= 48 )) {
333330 seed = rapid_mix (rapid_read64 (p ) ^ secret [0 ], rapid_read64 (p + 8 ) ^ seed );
334331 see1 = rapid_mix (rapid_read64 (p + 16 ) ^ secret [1 ], rapid_read64 (p + 24 ) ^ see1 );
@@ -343,13 +340,22 @@ RAPIDHASH_INLINE_CONSTEXPR uint64_t rapidhash_internal(const void *key, size_t l
343340 i -= 48 ;
344341 }
345342 }
343+ #else
344+ while (_likely_ (i >= 48 )) {
345+ seed = rapid_mix (rapid_read64 (p ) ^ secret [0 ], rapid_read64 (p + 8 ) ^ seed );
346+ see1 = rapid_mix (rapid_read64 (p + 16 ) ^ secret [1 ], rapid_read64 (p + 24 ) ^ see1 );
347+ see2 = rapid_mix (rapid_read64 (p + 32 ) ^ secret [2 ], rapid_read64 (p + 40 ) ^ see2 );
348+ p += 48 ;
349+ i -= 48 ;
350+ }
351+ #endif
346352 see3 ^= see4 ;
347353 see5 ^= see6 ;
348354 seed ^= see1 ;
349355 see3 ^= see2 ;
350356 seed ^= see5 ;
351357 seed ^= see3 ;
352- if (( i > 16 ) ) {
358+ if (i > 16 ) {
353359 seed = rapid_mix (rapid_read64 (p ) ^ secret [2 ], rapid_read64 (p + 8 ) ^ seed );
354360 if (RAPIDHASH_UNLIKELY_BULK (i > 32 ))
355361 seed = rapid_mix (rapid_read64 (p + 16 ) ^ secret [2 ], rapid_read64 (p + 24 ) ^ seed );
@@ -390,4 +396,3 @@ RAPIDHASH_INLINE_CONSTEXPR uint64_t rapidhash_withSeed(const void *key, size_t l
390396RAPIDHASH_INLINE_CONSTEXPR uint64_t rapidhash (const void * key , size_t len ) RAPIDHASH_NOEXCEPT {
391397 return rapidhash_withSeed (key , len , 0 );
392398}
393-
0 commit comments