The question is what values old_addr
and new_addr
can take. And why
they are uint64_t
, rather than simply int
. The simplest expression
would be:
new_addr = old_addr + std::min( delta, -static_cast<int>( old_addr ) );
, but if old_addr
can be greater than INT_MAX
, this won't work.
Otherwise, the rules of mixed signed/unsigned arithmetic in C/C++ are
such that you're probably safest using explicit if
s, and not risking
any mixed arithmetic before being sure of the values.
And note that on most machines, abs( delta )
will still be negative if
delta
is equal to INT_MIN
. To correctly handle all of the cases,
you'ld need something like:
if ( delta > 0 ) {
new_addr = std::numeric_limits<uin64_t>::max() - delta > old_addr
? old_addr + delta
: std::numeric_limits<uint64_t>::max();
} else if ( delta < 0 ) {
new_addr = old_addr != 0 && -(delta + 1) < old_addr - 1
? old_addr + delta
: 0;
} else {
new_addr = old_addr;
}
(Just off the top of my head. There could easily be an off by one error
in there.)