Bug 43783 - [4.5 Regression] -O -ftree-pre options compile libbid wrong
Summary: [4.5 Regression] -O -ftree-pre options compile libbid wrong
Status: RESOLVED FIXED
Alias: None
Product: gcc
Classification: Unclassified
Component: tree-optimization (show other bugs)
Version: 4.5.0
: P3 normal
Target Milestone: 4.5.1
Assignee: Richard Biener
URL:
Keywords: wrong-code
Depends on:
Blocks:
 
Reported: 2010-04-18 15:52 UTC by Roman Kononov
Modified: 2010-04-20 09:05 UTC (History)
1 user (show)

See Also:
Host: x86_64-unknown-linux-gnu
Target: x86_64-unknown-linux-gnu
Build: x86_64-unknown-linux-gnu
Known to work: 4.4.3 4.6.0
Known to fail: 4.5.0
Last reconfirmed: 2010-04-19 11:02:59


Attachments

Note You need to log in before you can comment on or make changes to this bug.
Description Roman Kononov 2010-04-18 15:52:49 UTC
$ cat test.c
#include <stdio.h>
int main() {
  _Decimal128 const a=1.111111111111111111111111111111111dl;
  _Decimal128 const b=1.1111111e-6158dl;
  _Decimal128 volatile x=a;
  _Decimal128 volatile y=b;
  double ab=a*b*1.0e6000dl;
  double xy=x*y*1.0e6000dl;
  printf("ab=%g\n",ab);
  printf("xy=%g\n",xy);
}

$ gcc test.c && ./a.out
ab=9.64506e-159
xy=9.64506e-159

$ gcc -O test.c && ./a.out
ab=1.23457e-158
xy=9.64506e-159

$ gcc --version | head -1
gcc (GCC) 4.5.1 20100418 (prerelease)

The correct value is 1.23457e-158:

$ echo "1.111111111111111111111111111111111*1.1111111" | bc
1.234567888888888888888888888888888

A simple modification of test.c can show that it is x*y and a*b, when computed by libbid, are incorrect. The a*b expression, when computed by gcc (with -O), is correct.

To further diagnose, I extracted libbid from the gcc source tree and compiled it outside of gcc to link it with the above test.c program. I added some #defines to compile the library and renamed some functions to call them directly from the test.

I found that if compiled with -O only, libbid multiplies correctly. With -O -ftree-pre, it multiplies incorrectly.

The real job is done by bid128_ext_fma() (about 3000 C lines).
Comment 1 Richard Biener 2010-04-18 18:22:07 UTC
This needs a testcase.  The libdecnumber code is a mess (and I can't find
an implementation for bid128_ext_fma()).
Comment 2 Roman Kononov 2010-04-18 18:34:01 UTC
(In reply to comment #1)
> This needs a testcase.  The libdecnumber code is a mess (and I can't find
> an implementation for bid128_ext_fma()).
> 

bid128_ext_fma() is in libgcc/config/libbid/bid128_fma.c
Comment 3 Roman Kononov 2010-04-19 04:25:05 UTC
Starting from r150519 gcc compiles its own internal libbid wrong.

With the previous revision of gcc, the output of the above test.c is correct:

$ gcc -O test.c && ./a.out
ab=1.23457e-158
xy=1.23457e-158
Comment 4 Richard Biener 2010-04-19 09:56:21 UTC
Confirmed (libbid result is incorrect, GCC constant-folded result is correct).
Comment 5 Richard Biener 2010-04-19 11:02:59 UTC
It's not bid128_ext_fma that is miscompiled but bid_round.c, building that
with -O1 [-ftree-pre] works [fails].

__bid_round192_39_57 is miscompiled by PRE.
Comment 6 Richard Biener 2010-04-19 11:20:26 UTC
Testcase:

typedef __attribute__((aligned(16)))
struct {
    unsigned long w[3];
} UINT192;

UINT192 __bid_Kx192[32];

extern void abort (void);

int main()
{
  int i = 0;
  unsigned long x = 0;
  for (i = 0; i < 32; ++i)
    __bid_Kx192[i].w[1] = i == 1;
  for (i = 0; i < 32; ++i)
    x += __bid_Kx192[1].w[1];
  if (x != 32)
    abort ();
  return 0;
}
Comment 7 Richard Biener 2010-04-19 11:57:45 UTC
The array element alignment is not properly visible, but instead loads of
random crap alignments appear in trees.
Comment 8 Richard Biener 2010-04-19 13:37:08 UTC
Subject: Bug 43783

Author: rguenth
Date: Mon Apr 19 13:36:54 2010
New Revision: 158517

URL: http://gcc.gnu.org/viewcvs?root=gcc&view=rev&rev=158517
Log:
2010-04-19  Richard Guenther  <rguenther@suse.de>

	PR tree-optimization/43783
	* tree-ssa-pre.c (create_component_ref_by_pieces_1): Drop
	constant ARRAY_REF operands two and three if possible.

	* gcc.c-torture/execute/pr43783.c: New testcase.

Added:
    trunk/gcc/testsuite/gcc.c-torture/execute/pr43783.c
Modified:
    trunk/gcc/ChangeLog
    trunk/gcc/testsuite/ChangeLog
    trunk/gcc/tree-ssa-pre.c

Comment 9 Roman Kononov 2010-04-19 20:46:43 UTC
The 4.5 branch works for me if patched this way.
Thanks.
Comment 10 Richard Biener 2010-04-20 09:05:51 UTC
Fixed.
Comment 11 Richard Biener 2010-04-20 09:05:57 UTC
Subject: Bug 43783

Author: rguenth
Date: Tue Apr 20 09:05:33 2010
New Revision: 158549

URL: http://gcc.gnu.org/viewcvs?root=gcc&view=rev&rev=158549
Log:
2010-04-20  Richard Guenther  <rguenther@suse.de>

	PR tree-optimization/43783
	* tree-ssa-pre.c (create_component_ref_by_pieces_1): Drop
	constant ARRAY_REF operands two and three if possible.

	* gcc.c-torture/execute/pr43783.c: New testcase.

Added:
    branches/gcc-4_5-branch/gcc/testsuite/gcc.c-torture/execute/pr43783.c
Modified:
    branches/gcc-4_5-branch/gcc/ChangeLog
    branches/gcc-4_5-branch/gcc/testsuite/ChangeLog
    branches/gcc-4_5-branch/gcc/tree-ssa-pre.c