This is the mail archive of the
gcc@gcc.gnu.org
mailing list for the GCC project.
Bug in optimization?
- From: Alexander Stante <mrpac at gmx dot de>
- To: gcc at gcc dot gnu dot org
- Date: Sat, 10 Jul 2004 22:50:59 +0200
- Subject: Bug in optimization?
Hello,
suppose the following code:
int main()
{
int x=10;
const int y[1] = {(x + x)};
x = y[0];
printf("%d\n",y[0]);
return 0;
}
If you compile it without optimization you get as result from printf
"20". If you compile it with the -O1 optimization switch on the result
is surpisingly 40.
If you look at the generated assembler source you see the following:
main:
pushl %ebp
movl %esp, %ebp
subl $8, %esp
andl $-16, %esp
movl $40, 4(%esp)
movl $.LC0, (%esp)
call printf
movl $0, %eax
movl %ebp, %esp
popl %ebp
ret
Where does "movl $40, 4(%esp)" come from?
One interesting notice is that if you add a additional "x = y[0];" just
before the printf you will get as result of the program "80", if you add
another one you will get "160" and so on and on.
If you read from 'x', for example with printf("%d\t%d\n",x,y[0]) you
will see that x and y[0] do not have the same value. When y[0]==80,
x==40, when y[0] = 160, x==80 and so on and on.
If you exchange the (x+x) above with (x*x) you will get the same
different results just with multiplication every time.
$ gcc -v
Reading specs from /usr/lib/gcc-lib/i486-linux/3.3.3/specs
Configured with: ../src/configure -v
--enable-languages=c,c++,java,f77,pascal,objc,ada,treelang --prefix=/usr
--mandir=/usr/share/man --infodir=/usr/share/info
--with-gxx-include-dir=/usr/include/c++/3.3 --enable-shared
--with-system-zlib --enable-nls --without-included-gettext
--enable-__cxa_atexit --enable-clocale=gnu --enable-debug
--enable-java-gc=boehm --enable-java-awt=xlib --enable-objc-gc i486-linux
Thread model: posix
gcc version 3.3.3 (Debian 20040401)
I also tried it on two other target compiler with the same wrong results
(C source with three of this x = y[0] assignments)
--------------------------------------------------
main:
@ args = 0, pretend = 0, frame = 0
@ frame_needed = 1, uses_anonymous_args = 0
mov ip, sp
stmfd sp!, {fp, ip, lr, pc}
sub fp, ip, #4
ldr r0, .L2
mov r1, #160
bl printf
mov r0, #0
ldmea fp, {fp, sp, pc}
$ arm-agb-elf-gcc -v
Reading specs from /usr/local/devkitadv/lib/gcc-lib/arm-agb-elf/3.1/specs
Configured with: ../gcc-3.1/configure --prefix=/usr/local/devkitadv
--target=arm-agb-elf --with-cpu=arm7tdmi --without-local-prefix
--with-newlib --with-headers=../newlib-1.10.0/newlib/libc/include/
--with-gc=simple --enable-multilib --enable-interwork
--enable-languages=c++ --enable-targets=arm-elf,arm-coff,arm-aout
--disable-threads -v
Thread model: single
gcc version 3.1 (Linux DevKit-Advance by Tom Badran tb100@doc.ic.ac.uk)
-------------------------------------------------
main:
link.w %a6,#0
pea 160.w
pea .LC0
jbsr printf
clr.l %d0
unlk %a6
rts
$ m68k-neogeo-elf-gcc -v
Reading specs from
/home/ice/Projekte/devkitng/bin/bin/../lib/gcc-lib/m68k-neogeo-elf/3.3.2/specs
Configured with: ../../gcc-3.3.2/configure --target=m68k-neogeo-elf
--prefix=/home/ice/Projekte/devkitng/bin/
Thread model: single
gcc version 3.3.2
Bye
Alex