2
0
mirror of https://gitlab.isc.org/isc-projects/bind9 synced 2025-08-22 01:59:26 +00:00

switch bit rotation functions to statement expressions

Using `static inline` functions in the headers break gcov as it cannot
properly track the hits. To fix the issue, convert the expressions to
statement macros. The added static assertions will ensure integer
promotion cannot occur unlike its previous function counterpart.
This commit is contained in:
Aydın Mercan 2025-08-21 15:24:40 +03:00
parent b7eb292121
commit 8e0c794046
No known key found for this signature in database
3 changed files with 91 additions and 51 deletions

View File

@ -72,52 +72,92 @@
#endif /* __has_header(<stdbit.h>) */
#define ISC_ROTATE_LEFT8(x, n) \
({ \
STATIC_ASSERT(__builtin_constant_p(n) == 1, \
"rotation amount must be constant"); \
STATIC_ASSERT( \
__builtin_types_compatible_p(typeof(x), uint8_t), \
"rotated value must be uint8_t"); \
((x) << n | (x) >> (8 - n)); \
})
#define ISC_ROTATE_LEFT16(x, n) \
({ \
STATIC_ASSERT(__builtin_constant_p(n) == 1, \
"rotation amount must be constant"); \
STATIC_ASSERT( \
__builtin_types_compatible_p(typeof(x), uint16_t), \
"rotated value must be uint16_t"); \
((x) << n | (x) >> (16 - n)); \
})
#define ISC_ROTATE_LEFT32(x, n) \
({ \
STATIC_ASSERT(__builtin_constant_p(n) == 1, \
"rotation amount must be constant"); \
STATIC_ASSERT( \
__builtin_types_compatible_p(typeof(x), uint32_t), \
"rotated value must be uint32_t"); \
((x) << n | (x) >> (32 - n)); \
})
#define ISC_ROTATE_LEFT64(x, n) \
({ \
STATIC_ASSERT(__builtin_constant_p(n) == 1, \
"rotation amount must be constant"); \
STATIC_ASSERT( \
__builtin_types_compatible_p(typeof(x), uint64_t), \
"rotated value must be uint64_t"); \
((x) << n | (x) >> (64 - n)); \
})
#define ISC_ROTATE_RIGHT8(x, n) \
({ \
STATIC_ASSERT(__builtin_constant_p(n) == 1, \
"rotation amount must be constant"); \
STATIC_ASSERT( \
__builtin_types_compatible_p(typeof(x), uint8_t), \
"rotated value must be uint8_t"); \
((x) >> n | (x) << (8 - n)); \
})
#define ISC_ROTATE_RIGHT16(x, n) \
({ \
STATIC_ASSERT(__builtin_constant_p(n) == 1, \
"rotation amount must be constant"); \
STATIC_ASSERT( \
__builtin_types_compatible_p(typeof(x), uint16_t), \
"rotated value must be uint16_t"); \
((x) >> n | (x) << (16 - n)); \
})
#define ISC_ROTATE_RIGHT32(x, n) \
({ \
STATIC_ASSERT(__builtin_constant_p(n) == 1, \
"rotation amount must be constant"); \
STATIC_ASSERT( \
__builtin_types_compatible_p(typeof(x), uint32_t), \
"rotated value must be uint32_t"); \
((x) >> n | (x) << (32 - n)); \
})
#define ISC_ROTATE_RIGHT64(x, n) \
({ \
STATIC_ASSERT(__builtin_constant_p(n) == 1, \
"rotation amount must be constant"); \
STATIC_ASSERT( \
__builtin_types_compatible_p(typeof(x), uint64_t), \
"rotated value must be uint64_t"); \
((x) >> n | (x) << (64 - n)); \
})
#if SIZE_MAX == UINT64_MAX
#define isc_rotate_leftsize(x, n) isc_rotate_left64(x, n)
#define isc_rotate_rightsize(x, n) isc_rotate_right64(x, n)
#define ISC_ROTATE_LEFTSIZE(x, n) ISC_ROTATE_LEFT64(x, n)
#define ISC_ROTATE_RIGHTSIZE(x, n) ISC_ROTATE_RIGHT64(x, n)
#elif SIZE_MAX == UINT32_MAX
#define isc_rotate_leftsize(x, n) isc_rotate_left32(x, n)
#define isc_rotate_rightsize(x, n) isc_rotate_right32(x, n)
#define ISC_ROTATE_LEFTSIZE(x, n) ISC_ROTATE_LEFT32(x, n)
#define ISC_ROTATE_RIGHTSIZE(x, n) ISC_ROTATE_RIGHT32(x, n)
#else
#error "size_t must be either 32 or 64-bits"
#endif
static inline uint8_t __attribute__((always_inline))
isc_rotate_left8(const uint8_t x, uint32_t n) {
return (x << n) | (x >> (8 - n));
}
static inline uint16_t __attribute__((always_inline))
isc_rotate_left16(const uint16_t x, uint32_t n) {
return (x << n) | (x >> (16 - n));
}
static inline uint32_t __attribute__((always_inline))
isc_rotate_left32(const uint32_t x, uint32_t n) {
return (x << n) | (x >> (32 - n));
}
static inline uint64_t __attribute__((always_inline))
isc_rotate_left64(const uint64_t x, uint32_t n) {
return (x << n) | (x >> (64 - n));
}
static inline uint8_t __attribute__((always_inline))
isc_rotate_right8(const uint8_t x, uint32_t n) {
return (x >> n) | (x << (8 - n));
}
static inline uint16_t __attribute__((always_inline))
isc_rotate_right16(const uint16_t x, uint32_t n) {
return (x >> n) | (x << (16 - n));
}
static inline uint32_t __attribute__((always_inline))
isc_rotate_right32(const uint32_t x, uint32_t n) {
return (x >> n) | (x << (32 - n));
}
static inline uint64_t __attribute__((always_inline))
isc_rotate_right64(const uint64_t x, uint32_t n) {
return (x >> n) | (x << (64 - n));
}

View File

@ -36,7 +36,7 @@
static inline size_t
fx_add_to_hash(size_t hash, size_t i) {
return isc_rotate_leftsize(hash, 5) ^ i * K;
return ISC_ROTATE_LEFTSIZE(hash, 5) ^ i * K;
}
/*

View File

@ -47,9 +47,9 @@
#define HALF_ROUND64(a, b, c, d, s, t) \
a += b; \
c += d; \
b = isc_rotate_left64(b, s) ^ a; \
d = isc_rotate_left64(d, t) ^ c; \
a = isc_rotate_left64(a, 32);
b = ISC_ROTATE_LEFT64(b, s) ^ a; \
d = ISC_ROTATE_LEFT64(d, t) ^ c; \
a = ISC_ROTATE_LEFT64(a, 32);
#define FULL_ROUND64(v0, v1, v2, v3) \
HALF_ROUND64(v0, v1, v2, v3, 13, 16); \
@ -60,9 +60,9 @@
#define HALF_ROUND32(a, b, c, d, s, t) \
a += b; \
c += d; \
b = isc_rotate_left32(b, s) ^ a; \
d = isc_rotate_left32(d, t) ^ c; \
a = isc_rotate_left32(a, 16);
b = ISC_ROTATE_LEFT32(b, s) ^ a; \
d = ISC_ROTATE_LEFT32(d, t) ^ c; \
a = ISC_ROTATE_LEFT32(a, 16);
#define FULL_ROUND32(v0, v1, v2, v3) \
HALF_ROUND32(v0, v1, v2, v3, 5, 8); \