This doesn't address the deeper problem, but we could also simplify the
whole function by just doing:
static size_t
find_common_mask(size_t val1, size_t val2)
{
size_t mask = ~0;
size_t diff = val1 ^ val2;
while (diff & mask)
mask <<= 1;
return mask;
}
Bit twiddling is such fun. And error prone. So I won't commit this; I'll
just attach the patch.
Index: src/dod.c
===================================================================
RCS file: /cvs/public/parrot/src/dod.c,v
retrieving revision 1.138
diff -u -r1.138 dod.c
--- src/dod.c 26 Oct 2004 15:01:29 -0000 1.138
+++ src/dod.c 26 Oct 2004 19:11:48 -0000
@@ -921,27 +921,13 @@
static size_t
find_common_mask(size_t val1, size_t val2)
{
- int i;
- int bound = sizeof(size_t) * 8;
+ size_t mask = ~0;
+ size_t diff = val1 ^ val2;
- /* Shifting a value by its size (in bits) or larger is undefined behaviour.
- so need an explict check to return 0 if there is no prefix, rather than
- attempting to rely on (say) 0xFFFFFFFF << 32 being 0 */
- for (i = 0; i < bound; i++) {
- if (val1 == val2) {
- return ~(size_t)0 << i;
- }
- val1 >>= 1;
- val2 >>= 1;
- }
- if (val1 == val2) {
- assert(i == bound);
- return 0;
- }
+ while (diff & mask)
+ mask <<= 1;
- internal_exception(INTERP_ERROR,
- "Unexpected condition in find_common_mask()!\n");
- return 0;
+ return mask;
}
/*