ash numeric overflow problem

Michael Abbott michael at araneidae.co.uk
Fri Jun 5 15:24:27 UTC 2009


On Fri, 5 Jun 2009, Denys Vlasenko wrote:
> On Fri, Jun 5, 2009 at 3:15 PM, Michael Abbott<michael at araneidae.co.uk> wrote:
> > On Fri, 5 Jun 2009, Michael Abbott wrote:
> > 1.13.3:
> >     $ echo $((0x80000000 & 1))
> >     0
> >
> > 1.14.1:
> >     $ echo $((0x80000000 & 1))
> >     1
> Looks like ash and bash act differently on arithmetic overflow.
> bash treats "too big" numbers as 0:
> 
> # echo $((0x8000000000000000))
> -9223372036854775808
> # echo $((0x80000000000000000))
> 0
> 
> and ash as -1 (all-ones). It just uses strtol internally, and that's
> what strtol returns.

Oh, how horrible.  I'd been assuming modulo-32-bit arithmetic.

> Quick fix is to use CONFIG_SH_MATH_SUPPORT_64=y. Perhaps this is
> what you inadvertently switched off (because option name
> has changed in 1.14.x).

Goodness me, you're quite right!  I didn't realise I was using 64-bit 
arithmetic...  That will fix my immediate problem, thank you.

> Complete fix is to add "errno = 0" and if() here in math.c:
> 
>                         errno = 0;
>                         numstackptr->val = strto_arith_t(expr, (char **) &expr, 0);
>                         if (errno)
>                                 numstackptr->val = 0; /* bash compat */
>                         goto num;
> 
> Does it work for you?

Well, I actually I'd rather have modulo-2^32 arithmetic everywhere.  
Maybe I'll see how easy it is to create such an option.

Unfortuately, as you say, strtol also doesn't like my numbers.  I stumbled 
across this earlier in another application.  In that case I've cheated and 
used strtoul -- that function actually handles '-' ok, and so I get away 
with using it on signed numbers.  

Have to say that truncation is giving me unpleasant surprises... I guess 
I'm too set in the mind-set of computer arithmetic being modulo word size.


P.S.  My message was sent as:

<tab-character>$ printf %x -2147483647

but came quoted from you as (looking at the raw mime):

> =A0 =A0 =A0 =A0$ printf %x -2147483647

My mailer (pine 4.64) was somewhat bemused by this, rendering this as

> ? ? ? ?$ printf %x -2147483647

Any idea where this mysterious translation happened?


More information about the busybox mailing list