From 6555fe19791476b034179149e33760b07f676c87 Mon Sep 17 00:00:00 2001 From: John Naylor Date: Wed, 29 Jan 2025 13:35:43 +0700 Subject: [PATCH] Revert "Speed up tail processing when hashing aligned C strings, take two" This reverts commit a365d9e2e8c1ead27203a4431211098292777d3b. Older versions of Valgrind raise an error, so go back to the bytewise loop for the final word in the input. Reported-by: Anton A. Melnikov Discussion: https://postgr.es/m/a3a959f6-14b8-4819-ac04-eaf2aa2e868d@postgrespro.ru Backpatch-through: 17 --- src/include/common/hashfn_unstable.h | 46 ++++++---------------------- 1 file changed, 10 insertions(+), 36 deletions(-) diff --git a/src/include/common/hashfn_unstable.h b/src/include/common/hashfn_unstable.h index 0adb0f82f9a..e67a4d3158d 100644 --- a/src/include/common/hashfn_unstable.h +++ b/src/include/common/hashfn_unstable.h @@ -219,13 +219,6 @@ fasthash_accum(fasthash_state *hs, const char *k, size_t len) #define haszero64(v) \ (((v) - 0x0101010101010101) & ~(v) & 0x8080808080808080) -/* get first byte in memory order */ -#ifdef WORDS_BIGENDIAN -#define firstbyte64(v) ((v) >> 56) -#else -#define firstbyte64(v) ((v) & 0xFF) -#endif - /* * all-purpose workhorse for fasthash_accum_cstring */ @@ -262,7 +255,7 @@ static inline size_t fasthash_accum_cstring_aligned(fasthash_state *hs, const char *str) { const char *const start = str; - uint64 chunk; + size_t remainder; uint64 zero_byte_low; Assert(PointerIsAligned(start, uint64)); @@ -282,7 +275,7 @@ fasthash_accum_cstring_aligned(fasthash_state *hs, const char *str) */ for (;;) { - chunk = *(uint64 *) str; + uint64 chunk = *(uint64 *) str; #ifdef WORDS_BIGENDIAN zero_byte_low = haszero64(pg_bswap64(chunk)); @@ -297,33 +290,14 @@ fasthash_accum_cstring_aligned(fasthash_state *hs, const char *str) str += FH_SIZEOF_ACCUM; } - if (firstbyte64(chunk) != 0) - { - size_t remainder; - uint64 mask; - - /* - * The byte corresponding to the NUL will be 0x80, so the rightmost - * bit position will be in the range 15, 23, ..., 63. Turn this into - * byte position by dividing by 8. - */ - remainder = pg_rightmost_one_pos64(zero_byte_low) / BITS_PER_BYTE; - - /* - * Create a mask for the remaining bytes so we can combine them into - * the hash. This must have the same result as mixing the remaining - * bytes with fasthash_accum(). - */ -#ifdef WORDS_BIGENDIAN - mask = ~UINT64CONST(0) << BITS_PER_BYTE * (FH_SIZEOF_ACCUM - remainder); -#else - mask = ~UINT64CONST(0) >> BITS_PER_BYTE * (FH_SIZEOF_ACCUM - remainder); -#endif - hs->accum = chunk & mask; - fasthash_combine(hs); - - str += remainder; - } + /* + * The byte corresponding to the NUL will be 0x80, so the rightmost bit + * position will be in the range 7, 15, ..., 63. Turn this into byte + * position by dividing by 8. + */ + remainder = pg_rightmost_one_pos64(zero_byte_low) / BITS_PER_BYTE; + fasthash_accum(hs, str, remainder); + str += remainder; return str - start; }