Java Solaris Communities Sun Store Join SDN My Profile Why Join?
 
Bug Database
Bug Detail
Quick Lists
Top 25 Bugs
Top 25 RFE's
Recently Closed Bugs
Printable Page Printable Page


Bug Database
Bug ID: 6654460
Votes 0
Synopsis [1.4.2] : 2 possible problems in shift operation in compiler2 (RHEL, IA64)
Category hotspot:compiler2
Reported Against
Release Fixed 1.4.2_18-rev(b10)
State 10-Fix Delivered, bug
Priority: 3-Medium
Related Bugs 6660833
Submit Date 24-JAN-2008
Description
The customer reported  2 possible problems in shift operation in compiler2.

-------------
1. Shift distance is more than 32 in int type variable.

PROBLEM DESCRIPTION:

Left-shift operation for int type variable causes incorrect result.
This problem occurs when the operator executes more than 32 bits shift.
Also, interpreter executes correctly. After VM context moves
to compiled code execution, incorrect result appears.

CONFIGURATION :
OS : Red Hat Enterprise Linux Server release 5 (Itanium)
     Red Hat Enterprise Linux AS release 4 (Itanium)
JDK : 1.4.2_14 / 1.4.2_16 Server VM


ABOUT REPRODUCING PROGRAM:
The attached program executes 11 << 38. The result is 0(zero).
However, the following is extracted from  "15.19 Shift Operators" of  JLS.
 "If the promoted type of the left-hand operand is int, 
   only the five lowest-order bits of the right-hand operand 
   are used as the shift distance."
 ( 11 << 38 ) = ( 11 << 6 ) = 704 seems correct.

INVESTIGATION :

The customer investigated the compiled code. The compiled code which always causes 0(zero)
is generated.

0x200000000392e076 e0  customer  00 18 40 00 :             and r46=r0,r0
0x200000000392e07c 00 00 04 00 11 00 :             nop.i 0x0;;
0x200000000392e080 11 00 b8 6e 90 11 : [MIB]       st4 [r55]=r46

They think the following (source) code at 3344 in ia64.ad causes the above-mentioned 
compiled code.

---- ./hotspot/src/cpu/ia64/vm/ia64.ad in 1.4.2_16 -------

  3338    enc_class emit_shlI_reg_imm6( gRegI dst, gRegI src, immI_1to64 cnt, pReg qp ) %{
  3339      MacroAssembler _masm(&cbuf);
  3340      if ( (int)$cnt$$constant < 32 )
  3341        __ depz( as_PredicateRegister($qp$$reg), as_Register($dst$$reg), as_Register($src$$reg),
  3342                 (int)$cnt$$constant, 32 - (int)$cnt$$constant );
  3343      else
  3344        __ and3( as_PredicateRegister($qp$$reg), as_Register($dst$$reg), GR0, GR0 );
  3345    %}

At the above line, when shift distance is more than 32, compiled code always causes 0.


REPRODUCING PROGRAM : 
------- ShlI.java ------
public class ShlI {
    public static       int value = 11;
    public static final int shift = 38;
    public static final int LOOPS = 10000;

    static void foo() {
        for (int i=0; i<LOOPS; i++) {
          if (i==LOOPS-1) {
              value = 11;
              System.out.print( value + " << " + shift + " = " );
          }
          value<<=shift;
          if (i==LOOPS-1) {
              System.out.println(value);
          }
        }
    }
    public static void main(String args[]) {
       for (int i=0; i<20; i++) {
         foo();
       }
    }
}
-------

COMMAND LINE :
% java ShlI
11 << 38 = 704
11 << 38 = 704
11 << 38 = 704
11 << 38 = 704
11 << 38 = 704
11 << 38 = 0
11 << 38 = 0
11 << 38 = 0
11 << 38 = 0
11 << 38 = 0
11 << 38 = 0
11 << 38 = 0
11 << 38 = 0
11 << 38 = 0
11 << 38 = 0
11 << 38 = 0
11 << 38 = 0
11 << 38 = 0
11 << 38 = 0
11 << 38 = 0


2. Shift distance is more than 64 in long type variable.

PROBLEM DESCRIPTION :

The following shift function for long type variable is provided.
However, when the shift distance is more than 64 in long type variable,
"64 - (int)$cnt$$constant"  will be negative number.
This might generate incorrect compiled code.

---- ./hotspot/src/cpu/ia64/vm/ia64.ad in 1.4.2_16 -----
.....
  3347    enc_class emit_shlL_reg_imm6( gRegL dst, gRegL src, gRegI cnt, pReg qp ) %{
  3348      MacroAssembler _masm(&cbuf);
  3349      __ depz( as_PredicateRegister($qp$$reg), as_Register($dst$$reg), as_Register($src$$reg),
  3350               (int)$cnt$$constant, 64 - (int)$cnt$$constant );
  3351    %}
......
Posted Date : 2008-01-24 01:38:11.0
Work Around
N/A
Evaluation
Changes required in assembly macros in ia64.ad
Customer has made suggestions.
Posted Date : 2008-03-12 09:02:07.0

In addition,   xxxxx@xxxxx   has pointed out why the customer's second point does not cause a failure for long values with >64 bit shift distances:
"
In this snippet:

 3347    enc_class emit_shlL_reg_imm6( gRegL dst, gRegL src, gRegI cnt, pReg qp ) %{
 3348      MacroAssembler _masm(&cbuf);
 3349      __ depz( as_PredicateRegister($qp$$reg), as_Register($dst$$reg), as_Register($src$$reg),
 3350               (int)$cnt$$constant, 64 - (int)$cnt$$constant );
 3351    %}

cnt is actually of type immI_1to64 which guarantees it's in range.  The emit functions don't actually pay any attention to the type declared in the emit definition.  That are actually more like macros which are substituted back into their uses and pick up the types at the uses.
"

So the fix this will address 32-bit int shifts only.
Posted Date : 2008-06-20 12:58:14.0
Comments
  
  Include a link with my name & email   


PLEASE NOTE: JDK6 is formerly known as Project Mustang