Bug 7719 - gcc with -O2 generates wrong code
Summary: gcc with -O2 generates wrong code
Status: RESOLVED DUPLICATE of bug 323
Alias: None
Product: gcc
Classification: Unclassified
Component: rtl-optimization (show other bugs)
Version: 3.0.4
: P3 normal
Target Milestone: ---
Assignee: Not yet assigned to anyone
URL:
Keywords: wrong-code
Depends on:
Blocks:
 
Reported: 2002-08-25 17:36 UTC by petr.savicky
Modified: 2005-04-20 07:10 UTC (History)
3 users (show)

See Also:
Host: i486-suse-linux-gnu
Target: i486-suse-linux-gnu
Build: i486-suse-linux-gnu
Known to work:
Known to fail:
Last reconfirmed:


Attachments

Note You need to log in before you can comment on or make changes to this bug.
Description petr.savicky 2002-08-25 17:36:00 UTC
If compiled with -O2, then at some step of the computation,
line 3284 of grow.i (line 400 of grow.c), i.e.
        if (val >= devtarget || val >= *bval) return;
does not perform the return command, although all the
variables val, *bval, devtarget are equal.

The commands at lines 3285-3290 in grow.i print
GROW:   5.924155689933546576 val
GROW:   5.924155689933546576 devtarget
GROW:   5.924155689933546576 *bval
GROW:   0.000000e+00 *bval-val

This behaviour is fully deterministic.
If compiled without -O2, these lines do not occur in the output.

Release:
3.0.4 (SuSE), also 2.95.3 (SuSE) and 2.91.66 (RedHat)

Environment:
System: Linux linux 2.4.18-4GB #1 Fri Apr 5 15:14:39 UTC 2002 i686 unknown
Architecture: i686

host: i486-suse-linux-gnu
build: i486-suse-linux-gnu
target: i486-suse-linux-gnu
configured with: ../configure --enable-threads=posix --enable-long-long --prefix=/opt/experimental --with-local-prefix=/usr/local --enable-languages=c,c++,f77,objc,java --disable-nls --enable-shared i486-suse-linux

The exact set of compile options used is:
gcc -I$RBASE/include 
    -I/usr/local/include
    -D__NO_MATH_INLINES
    -mieee-fp 
    -fPIC 
    -g
    -O2
    -c grow.c -o grow.o

I tested the problem on three different computers (all PCs with linux).
The above info is from one of them.

How-To-Repeat:
The preprocessed source code is http://www.cs.cas.cz/~savicky/R_tree/grow.i

If you need to run the program in the situation, when the
error appears, it is necessary to install R-1.5.1
(www.r-project.org) with the default settings, i.e. with -O2
in gcc and g++ options. Then, perform the following steps:

1. put http://www.cs.cas.cz/~savicky/R_tree/tree_o2_error-3.tar.gz
   and http://www.cs.cas.cz/~savicky/R_tree/corrupt_tree_o2-2.tar.gz
   into a work directory and cd to this directory.

2. tar -zxf tree_o2_error-3.tar.gz
   tar -zxf corrupt_tree_o2-2.tar.gz

3. R CMD INSTALL tree/

4. cd corrupt_tree

5. R (this should give you the R prompt)

6. source("script.R") (in the R prompt)

This should produce the lines with "GROW" copied above.

The problem is indeed in a wrong compilation of grow.c.
If this file alone is compiled without -O2, linked
together with treefix.o into tree.so and copied to
$RBASE/library/tree/libs/, the problem disappears.
(The script tree/src/recompile.sh, which I used for
this recompilation on my computer is included in the
tar package).
Comment 1 petr.savicky 2002-08-25 17:36:00 UTC
Fix:
Don't use optimization.
Comment 2 Eric Botcazou 2003-02-19 08:35:13 UTC
State-Changed-From-To: open->feedback
State-Changed-Why: Probably not a bug. On x86, at -O2, floating point values
    may be kept in FP registers when doing comparison with
    others stored in memory. Now x86 FP registers have
    extra-precision over a 'double', which may invalid
    an equality comparison. Compile your code with '-ffloat-store'
    if it relies on exact IEEE floating-point semantics.
Comment 3 petr.savicky 2003-02-19 15:28:47 UTC
From: Petr.Savicky@ff.cuni.cz
To: ebotcazou@gcc.gnu.org, Petr.Savicky@cuni.cz, gcc-bugs@gcc.gnu.org,
  gcc-prs@gcc.gnu.org, nobody@gcc.gnu.org, gcc-gnats@gcc.gnu.org
Cc:  
Subject: Re: optimization/7719: gcc with -O2 generates wrong code
Date: Wed, 19 Feb 2003 15:28:47 +0100

 On Wed, Feb 19, 2003 at 08:35:13AM -0000, ebotcazou@gcc.gnu.org wrote:
 > Synopsis: gcc with -O2 generates wrong code
 > 
 > State-Changed-From-To: open->feedback
 > State-Changed-By: ebotcazou
 > State-Changed-When: Wed Feb 19 08:35:13 2003
 > State-Changed-Why:
 >     Probably not a bug. On x86, at -O2, floating point values
 >     may be kept in FP registers when doing comparison with
 >     others stored in memory. Now x86 FP registers have
 >     extra-precision over a 'double', which may invalid
 >     an equality comparison. Compile your code with '-ffloat-store'
 >     if it relies on exact IEEE floating-point semantics.
 
 Yes, using -O2 together with -ffloat-store eliminates the problem.
 Moreover, the fact that a double value may change just by storing
 and reloading from memory explains the behaviour of the program.
 
 OK, this is not a bug of the compiler itself, but it is a bug in
 the default settings of gcc on x86. Everybody knows that the results
 of computer arithmetic are not safe, may have different results on
 different processors and definitely do not satisfy things like
 (a+b)+c = a+(b+c). Here, however, the problem is not in the operations
 with the numbers, but with keeping their values untouched. The value of a
 variable changes during a sequence of operations which do not involve it.
 The change may influence not only equality tests, but also inequality
 tests, which cannot be avoided. This is hard to accept as a correct
 behaviour even on a processor with a conceptually buggy design.
 
 The current success of GNU Project heavily relies on using its
 software on x86. Perhaps, this may be a reason to be more friendly
 to this processor and put -ffloat-store into the definition of -O2,
 which is frequently used as a default.
 
 For me as a Linux user, it was not nice to have the bug only under Linux
 and not under Windows, just because the Windows version was compiled
 by a different compiler.
 
 Best wishes
 
   Petr Savicky

Comment 4 Eric Botcazou 2003-02-19 15:53:38 UTC
From: Eric Botcazou <ebotcazou@libertysurf.fr>
To: Petr.Savicky@ff.cuni.cz
Cc: gcc-bugs@gcc.gnu.org,
 nobody@gcc.gnu.org,
 gcc-gnats@gcc.gnu.org
Subject: Re: optimization/7719: gcc with -O2 generates wrong code
Date: Wed, 19 Feb 2003 15:53:38 +0100

 > Yes, using -O2 together with -ffloat-store eliminates the problem.
 > Moreover, the fact that a double value may change just by storing
 > and reloading from memory explains the behaviour of the program.
 
 Thanks for the quick feedback.
 
 > OK, this is not a bug of the compiler itself, but it is a bug in
 > the default settings of gcc on x86. Everybody knows that the results
 > of computer arithmetic are not safe, may have different results on
 > different processors and definitely do not satisfy things like
 > (a+b)+c = a+(b+c). Here, however, the problem is not in the operations
 > with the numbers, but with keeping their values untouched. The value of a
 > variable changes during a sequence of operations which do not involve it.
 > The change may influence not only equality tests, but also inequality
 > tests, which cannot be avoided. This is hard to accept as a correct
 > behaviour even on a processor with a conceptually buggy design.
 
 You might want to try '-march=pentium[34] -mfpmath=sse' then, if you have of 
 course the right hardware.
 
 > The current success of GNU Project heavily relies on using its
 > software on x86. Perhaps, this may be a reason to be more friendly
 > to this processor and put -ffloat-store into the definition of -O2,
 > which is frequently used as a default.
 
 As someone else said, '-ffloat-store' is a big hammer which seriously harms
 the runtime performance of programs.
 
 -- 
 Eric Botcazou
Comment 5 Eric Botcazou 2003-03-14 11:30:49 UTC
State-Changed-From-To: feedback->closed
State-Changed-Why: Not a bug.
Comment 6 Andrew Pinski 2005-04-20 03:00:23 UTC
Reopening to ...
Comment 7 Andrew Pinski 2005-04-20 03:00:42 UTC
Mark as a dup of bug 323.

*** This bug has been marked as a duplicate of 323 ***