30 lines
783 B
C
30 lines
783 B
C
typedef unsigned long long uint64_t;
|
|
void f(uint64_t *a, uint64_t aa) __attribute__((noinline));
|
|
void f(uint64_t *a, uint64_t aa)
|
|
{
|
|
uint64_t new_value = aa;
|
|
uint64_t old_value = *a;
|
|
int bit_size = 32;
|
|
uint64_t mask = (uint64_t)(unsigned)(-1);
|
|
uint64_t tmp = old_value & mask;
|
|
new_value &= mask;
|
|
/* On overflow we need to add 1 in the upper bits */
|
|
if (tmp > new_value)
|
|
new_value += 1ull<<bit_size;
|
|
/* Add in the upper bits from the old value */
|
|
new_value += old_value & ~mask;
|
|
*a = new_value;
|
|
}
|
|
int main(void)
|
|
{
|
|
uint64_t value, new_value, old_value;
|
|
value = 0x100000001;
|
|
old_value = value;
|
|
new_value = (value+1)&(uint64_t)(unsigned)(-1);
|
|
f(&value, new_value);
|
|
if (value != old_value+1)
|
|
__builtin_abort ();
|
|
return 0;
|
|
}
|
|
|