United StatesChange Country, Oracle Worldwide Web Sites Communities I am a... I want to...
JDK-4971887 : Incorrect floating-point arithmetic or loop unrolling with -server -Xcomp option

Details
Type:
Bug
Submit Date:
2003-12-22
Status:
Resolved
Updated Date:
2004-01-21
Project Name:
JDK
Resolved Date:
2004-01-21
Component:
hotspot
OS:
solaris_9,solaris_8,solaris_10,solaris_nevada
Sub-Component:
compiler
CPU:
sparc
Priority:
P3
Resolution:
Fixed
Affected Versions:
1.4.2,1.4.2_12,5.0
Fixed Versions:
5.0 (b35)

Related Reports
Backport:
Duplicate:
Relates:

Sub Tasks

Description
Name: tb29552			Date: 12/22/2003


FULL PRODUCT VERSION :
java version "1.4.2_03"
Java(TM) 2 Runtime Environment, Standard Edition (build 1.4.2_03-b02)
Java HotSpot(TM) Client VM (build 1.4.2_03-b02, mixed mode)


FULL OS VERSION :
SunOS ussunx4 5.8 Generic_108528-10 sun4u sparc SUNW,Sun-Blade-1000

EXTRA RELEVANT SYSTEM CONFIGURATION :
  Program is actually running as part of the J2EE application on the JBoss 3.2 server.

A DESCRIPTION OF THE PROBLEM :
The attached program does not add up integers correctly when using the Hotspot server compiler.

This bug may be related to 4843257.  However, 4843257 was closed int Apr 2003, and this bug still occurs on Solaris.

I was unable to reproduce the bug on Windows.






STEPS TO FOLLOW TO REPRODUCE THE PROBLEM :
Compile attached program: "javac Bug.java"
Run program: "java -server -Xcomp Bug"

EXPECTED VERSUS ACTUAL BEHAVIOR :
EXPECTED -
total=1118.0

ACTUAL -
total=-1.8014390618947024E16

REPRODUCIBILITY :
This bug can be reproduced always.

---------- BEGIN SOURCE ----------
public class Bug
{
    public static double calcTotal ( long[] counts )
    {
        double total = 0;
        for ( int i=0; i < counts.length; i++ )
        {
            total += counts[i];
        }
        return ( total );
    }
    
    public static void main ( String[] args )
    {
       long[] counts = new long[] {
                113,64,23,56,98,48,33,101,8,14,27,58,17,6,
                121,18,3,3,24,13,58,14,23,14,4,123,29,5 };
       double total = Bug.calcTotal( counts );
       System.out.println( "total=" + total );
    }
}
---------- END SOURCE ----------

CUSTOMER SUBMITTED WORKAROUND :
The program work CORRECTLY if I disable loop unrolling:
   java -server -Xcomp -XX:LoopUnrollLimit=0 Bug

It also works CORRECTLY if I I disable the Hotspot server compiler:
   java -Xcomp Bug
Unfortunately this has a negetice effect on overall system performance.
(Review ID: 231819) 
======================================================================

                                    

Comments
SUGGESTED FIX

PRT webrev:

/net/prt-archiver.sfbay/data/archived_workspaces/main/c2_baseline/2004/20040112072047.rasbold.c2_baseline/workspace/webrevs/webrev-2004.01.12/index.html
                                     
2006-05-04
CONVERTED DATA

BugTraq+ Release Management Values

COMMIT TO FIX:
tiger-beta2

FIXED IN:
tiger-beta2

INTEGRATED IN:
tiger-b35
tiger-beta2


                                     
2004-06-14
PUBLIC COMMENTS

.
                                     
2004-06-10
SUGGESTED FIX

--- sparc.ad	Tue Jan  6 10:04:43 2004
***************
*** 7833,7851 ****
  instruct convL2D_reg_slow_fxtof(regD dst, stackSlotL src) %{
    match(Set dst (ConvL2D src));
    ins_cost(DEFAULT_COST*8 + MEMORY_REF_COST*6);
  
    expand %{
!     regD       tmpsrc;
      iRegI      ix43300000;
      iRegI      ix41f00000;
      stackSlotL lx43300000;
      stackSlotL lx41f00000;
!     regD       dx43300000;
      regD       dx41f00000;
      regD       tmp1;
!     regD       tmp2;
      regD       tmp3;
      regD       tmp4;
  
      stkL_to_regD_0(tmpsrc, src);
  
--- 7833,7851 ----
  instruct convL2D_reg_slow_fxtof(regD dst, stackSlotL src) %{
    match(Set dst (ConvL2D src));
    ins_cost(DEFAULT_COST*8 + MEMORY_REF_COST*6);
  
    expand %{
!     regD_low   tmpsrc;
      iRegI      ix43300000;
      iRegI      ix41f00000;
      stackSlotL lx43300000;
      stackSlotL lx41f00000;
!     regD_low   dx43300000;
      regD       dx41f00000;
      regD       tmp1;
!     regD_low   tmp2;
      regD       tmp3;
      regD       tmp4;
  
      stkL_to_regD_0(tmpsrc, src);
  
***************
*** 7902,7920 ****
  instruct convL2F_reg_slow_fxtof(regF dst, stackSlotL src) %{
    match(Set dst (ConvL2F src));
    ins_cost(DEFAULT_COST*9 + MEMORY_REF_COST*6);
  
    expand %{
!     regD       tmpsrc;
      iRegI      ix43300000;
      iRegI      ix41f00000;
      stackSlotL lx43300000;
      stackSlotL lx41f00000;
!     regD       dx43300000;
      regD       dx41f00000;
      regD       tmp1;
!     regD       tmp2;
      regD       tmp3;
      regD       tmp4;
      regD       tmp5;
  
      stkL_to_regD_0(tmpsrc, src);
--- 7902,7920 ----
  instruct convL2F_reg_slow_fxtof(regF dst, stackSlotL src) %{
    match(Set dst (ConvL2F src));
    ins_cost(DEFAULT_COST*9 + MEMORY_REF_COST*6);
  
    expand %{
!     regD_low   tmpsrc;
      iRegI      ix43300000;
      iRegI      ix41f00000;
      stackSlotL lx43300000;
      stackSlotL lx41f00000;
!     regD_low   dx43300000;
      regD       dx41f00000;
      regD       tmp1;
!     regD_low   tmp2;
      regD       tmp3;
      regD       tmp4;
      regD       tmp5;
  
      stkL_to_regD_0(tmpsrc, src);

###@###.### 2004-01-06
                                     
2004-01-06
EVALUATION

The problem is not a loop unrolling bug, but register allocation bug which is
exposed by the register pressure created, in this case, by loop unrolling.

The register allocation is attempting to use high double regs (f32-f62) in places where only a float register (f0-f31) is allowed.  The encoding generated by the compiler's assembler is interpreted as a completely different float register than the double intended, and bad values creep into the system.

The register allocation issue is a direct result of using register masks for the wrong operand type as generated by adlc.  At first glance, it appears that the problem is limited to operand casting in expand rules in .ad files. 

The simplest fix is to adjust the declarations for instruction sequences convL2D_reg_slow_fxtof and convL2F_reg_slow_fxtof in sparc.ad.

The source for this bug is the same as the source for a bug 4971850, which is
a different problem.

###@###.### 2003-12-24

I've add a suggested fix which will correct this problem.

However, Azeem's proposed fix for 1.5.0 bug 4971850 (which is concurrently open), will fix this bug, too, by eliminating the very code I am suggesting to correct.

I am reassigning this bug to him, and he will determine which fix is most
appropriate for 1.4.2.

###@###.### 2004-01-06
                                     
2004-01-06
WORK AROUND



Name: tb29552			Date: 12/22/2003


Add -XX:LoopUnrollLimit=0 to the run flags.

###@###.###  2003-12-22

======================================================================
                                     
2003-12-22



Hardware and Software, Engineered to Work Together