Name: ks84122 Date: 06/10/2002
The example below demonstrates that the 64 bit server compiler generates
poor array copying code. Reproducible on Solaris 9, Solaris 7 in 64 bit
mode, JDK 1.4.1 (solaris-sparcv9)
Original description from HP:
=============================
public class copybench
{
static char[] source = new char[2000];
static char[] target = new char[5000];
public static long run(int loopcount, boolean usesystem, int source_off,
int target_off, int len)
{
int indx, indx2;
long starttime = System.currentTimeMillis();
char[] s = source;
char[] t = target;
for (indx2=loopcount; --indx2 >= 0; )
{
if (! usesystem)
{
for (indx = 0; indx < len; ++indx)
{
t[target_off + indx] = s[source_off + indx];
}
}
else
{
System.arraycopy(s, source_off, t, target_off, len);
}
}
long endtime = System.currentTimeMillis();
return endtime - starttime;
}
public static void main(String argv[])
{
int indx;
for (indx=0; indx < source.length; ++indx)
{
source[indx] = (char) indx;
}
System.out.println((argv.length == 0) + " warmup " + (long) argv.length);
run(2,true,0,0,2000);
run(2,false,0,0,2000);
for (indx=100000; indx > 0; --indx)
{
run(1,true,1,1,16); // warm up run
run(1,false,1,1,16); // warm up run
}
System.out.println("start");
for (indx=10; indx > 0; --indx)
{
System.out.println("system copy " + run(99990,true,240,200,20));
System.out.println("java copy " + run(99990,false,240,200,20));
}
}
}
7%/export/home1/jgragg/jdk1.4.0_01/bin/java -server copybench
...
system copy 38
java copy 28
8%/export/home1/jgragg/jdk1.4.0_01/bin/java -d64 -server copybench
...
system copy 31
java copy 52 (52 ms vs 28 ms is almost 2x slower)
When I look at the assembly code generated, the 32 bit jvm generates
a clean unrolled copying loop. The 64 bit jvm generates something
that is quite ugly and slower code.
(Review ID: 153345)
======================================================================