Shifting: what's going on?
Facundo Ciccioli
facundofc@gmail.com
Thu Mar 29 15:05:00 GMT 2007
I expect to get a 1 in the s-th bit of a, and zeroes in all other
bits. I don't know why you say that's an arithmetic overflow, if
unsigned long long is 64 bits long and it has a 63-th bit (the last
one).
Anyway, Rupert Wood comment works, thanks a lot.
FaQ
2007/3/29, Andrew Haley <aph@redhat.com>:
> Facundo Ciccioli writes:
> > Hi. What follows applies to gcc (GCC) 3.4.2 (mingw-special), platform
> > x86-32bits.
> >
> > This code:
> >
> > int main() {
> > unsigned long long a= 1;
> > unsigned s= 63;
> >
> > a= (a << s);
> >
> > return 0;
> > }
> > generates this assembler (removing preamble and prologue stuff):
> >
> > movl $1, -8(%ebp)
> > movl $0, -4(%ebp)
> > movl $63, -12(%ebp)
> > movl -12(%ebp), %ecx
> > movl -8(%ebp), %eax
> > movl -4(%ebp), %edx
> > shldl %cl,%eax, %edx
> > sall %cl, %eax
> > testb $32, %cl
> > je L2
> > movl %eax, %edx
> > movl $0, %eax
> > L2:
> > movl %eax, -8(%ebp)
> > movl %edx, -4(%ebp)
> >
> > This is fine, and works as I expect.
> > However, this code:
> >
> > int main() {
> > unsigned long long a;
> > unsigned s= 63;
> >
> > a= (1 << s);
> >
> > return 0;
> > }
> > generates this assembler:
> >
> > movl $63, -12(%ebp)
> > movl -12(%ebp), %ecx
> > movl $1, %eax
> > sall %cl, %eax
> > cltd
> > movl %eax, -8(%ebp)
> > movl %edx, -4(%ebp)
> > which is... wrong. Not only the results aren't what they should, but
> > looking a little harder, the assembler generated doesn't seem to make
> > sense. What's with the CLTD instruction there? If I change s (the
> > shifted amount) to be 63 (31 is equivalent, because only 5 bits of %cl
> > are used) then the result are a bunch of 1's because the sign of %eax
> > goes all over %edx. And that's only one problem. If s is between 62
> > and 32, the 1 appears in %eax instead of being in %edx, where it
> > should.
> >
> > This is obviusly not urgent, since the first code is perfectly
> > acceptable and applicable to what I am doing, but I just got curious.
>
> This is an arithmetic overflow, and is explicitly undefined. One
> result is as good as any other. What do you expect the code to do?
>
> Andrew.
>
> --
> Red Hat UK Ltd, Amberley Place, 107-111 Peascod Street, Windsor, Berkshire, SL4 1TE, UK
> Registered in England and Wales No. 3798903
>
More information about the Gcc-help
mailing list