6946040: add intrinsic for short and char reverseBytes

Mon, 26 Apr 2010 11:27:21 -0700

author
never
date
Mon, 26 Apr 2010 11:27:21 -0700
changeset 1831
d7f654633cfe
parent 1820
bc32f286fae0
child 1832
b4776199210f

6946040: add intrinsic for short and char reverseBytes
Reviewed-by: never, twisti
Contributed-by: Hiroshi Yamauchi <yamauchi@google.com>

make/linux/makefiles/adlc.make file | annotate | diff | comparison | revisions
make/solaris/makefiles/adlc.make file | annotate | diff | comparison | revisions
src/cpu/sparc/vm/assembler_sparc.hpp file | annotate | diff | comparison | revisions
src/cpu/sparc/vm/sparc.ad file | annotate | diff | comparison | revisions
src/cpu/x86/vm/x86_32.ad file | annotate | diff | comparison | revisions
src/cpu/x86/vm/x86_64.ad file | annotate | diff | comparison | revisions
src/share/vm/adlc/formssel.cpp file | annotate | diff | comparison | revisions
src/share/vm/classfile/vmSymbols.hpp file | annotate | diff | comparison | revisions
src/share/vm/opto/classes.hpp file | annotate | diff | comparison | revisions
src/share/vm/opto/library_call.cpp file | annotate | diff | comparison | revisions
src/share/vm/opto/subnode.hpp file | annotate | diff | comparison | revisions
test/compiler/6431242/Test.java file | annotate | diff | comparison | revisions
test/compiler/6946040/TestCharShortByteSwap.java file | annotate | diff | comparison | revisions
     1.1 --- a/make/linux/makefiles/adlc.make	Tue Apr 20 13:26:33 2010 -0700
     1.2 +++ b/make/linux/makefiles/adlc.make	Mon Apr 26 11:27:21 2010 -0700
     1.3 @@ -127,6 +127,9 @@
     1.4  # Note that product files are updated via "mv", which is atomic.
     1.5  TEMPDIR := $(OUTDIR)/mktmp$(shell echo $$$$)
     1.6  
     1.7 +# Debuggable by default
     1.8 +CFLAGS += -g
     1.9 +
    1.10  # Pass -D flags into ADLC.
    1.11  ADLCFLAGS += $(SYSDEFS)
    1.12  
    1.13 @@ -135,7 +138,7 @@
    1.14  
    1.15  # Normally, debugging is done directly on the ad_<arch>*.cpp files.
    1.16  # But -g will put #line directives in those files pointing back to <arch>.ad.
    1.17 -#ADLCFLAGS += -g
    1.18 +ADLCFLAGS += -g
    1.19  
    1.20  ifdef LP64
    1.21  ADLCFLAGS += -D_LP64
     2.1 --- a/make/solaris/makefiles/adlc.make	Tue Apr 20 13:26:33 2010 -0700
     2.2 +++ b/make/solaris/makefiles/adlc.make	Mon Apr 26 11:27:21 2010 -0700
     2.3 @@ -147,6 +147,9 @@
     2.4  # Note that product files are updated via "mv", which is atomic.
     2.5  TEMPDIR := $(OUTDIR)/mktmp$(shell echo $$$$)
     2.6  
     2.7 +# Debuggable by default
     2.8 +CFLAGS += -g
     2.9 +
    2.10  # Pass -D flags into ADLC.
    2.11  ADLCFLAGS += $(SYSDEFS)
    2.12  
    2.13 @@ -155,7 +158,7 @@
    2.14  
    2.15  # Normally, debugging is done directly on the ad_<arch>*.cpp files.
    2.16  # But -g will put #line directives in those files pointing back to <arch>.ad.
    2.17 -#ADLCFLAGS += -g
    2.18 +ADLCFLAGS += -g
    2.19  
    2.20  ifdef LP64
    2.21  ADLCFLAGS += -D_LP64
     3.1 --- a/src/cpu/sparc/vm/assembler_sparc.hpp	Tue Apr 20 13:26:33 2010 -0700
     3.2 +++ b/src/cpu/sparc/vm/assembler_sparc.hpp	Mon Apr 26 11:27:21 2010 -0700
     3.3 @@ -661,9 +661,6 @@
     3.4      stx_op3      = 0x0e,
     3.5      swap_op3     = 0x0f,
     3.6  
     3.7 -    lduwa_op3    = 0x10,
     3.8 -    ldxa_op3     = 0x1b,
     3.9 -
    3.10      stwa_op3     = 0x14,
    3.11      stxa_op3     = 0x1e,
    3.12  
     4.1 --- a/src/cpu/sparc/vm/sparc.ad	Tue Apr 20 13:26:33 2010 -0700
     4.2 +++ b/src/cpu/sparc/vm/sparc.ad	Mon Apr 26 11:27:21 2010 -0700
     4.3 @@ -923,38 +923,6 @@
     4.4  #endif
     4.5  }
     4.6  
     4.7 -void emit_form3_mem_reg_asi(CodeBuffer &cbuf, const MachNode* n, int primary, int tertiary,
     4.8 -                        int src1_enc, int disp32, int src2_enc, int dst_enc, int asi) {
     4.9 -
    4.10 -  uint instr;
    4.11 -  instr = (Assembler::ldst_op << 30)
    4.12 -        | (dst_enc        << 25)
    4.13 -        | (primary        << 19)
    4.14 -        | (src1_enc       << 14);
    4.15 -
    4.16 -  int disp = disp32;
    4.17 -  int index    = src2_enc;
    4.18 -
    4.19 -  if (src1_enc == R_SP_enc || src1_enc == R_FP_enc)
    4.20 -    disp += STACK_BIAS;
    4.21 -
    4.22 -  // We should have a compiler bailout here rather than a guarantee.
    4.23 -  // Better yet would be some mechanism to handle variable-size matches correctly.
    4.24 -  guarantee(Assembler::is_simm13(disp), "Do not match large constant offsets" );
    4.25 -
    4.26 -  if( disp != 0 ) {
    4.27 -    // use reg-reg form
    4.28 -    // set src2=R_O7 contains offset
    4.29 -    index = R_O7_enc;
    4.30 -    emit3_simm13( cbuf, Assembler::arith_op, index, Assembler::or_op3, 0, disp);
    4.31 -  }
    4.32 -  instr |= (asi << 5);
    4.33 -  instr |= index;
    4.34 -  uint *code = (uint*)cbuf.code_end();
    4.35 -  *code = instr;
    4.36 -  cbuf.set_code_end(cbuf.code_end() + BytesPerInstWord);
    4.37 -}
    4.38 -
    4.39  void emit_call_reloc(CodeBuffer &cbuf, intptr_t entry_point, relocInfo::relocType rtype, bool preserve_g2 = false, bool force_far_call = false) {
    4.40    // The method which records debug information at every safepoint
    4.41    // expects the call to be the first instruction in the snippet as
    4.42 @@ -1954,11 +1922,6 @@
    4.43                         $mem$$base, $mem$$disp, $mem$$index, $dst$$reg);
    4.44    %}
    4.45  
    4.46 -  enc_class form3_mem_reg_little( memory mem, iRegI dst) %{
    4.47 -    emit_form3_mem_reg_asi(cbuf, this, $primary, -1,
    4.48 -                     $mem$$base, $mem$$disp, $mem$$index, $dst$$reg, Assembler::ASI_PRIMARY_LITTLE);
    4.49 -  %}
    4.50 -
    4.51    enc_class form3_mem_prefetch_read( memory mem ) %{
    4.52      emit_form3_mem_reg(cbuf, this, $primary, -1,
    4.53                         $mem$$base, $mem$$disp, $mem$$index, 0/*prefetch function many-reads*/);
    4.54 @@ -4311,8 +4274,8 @@
    4.55  // instructions for every form of operand when the instruction accepts
    4.56  // multiple operand types with the same basic encoding and format.  The classic
    4.57  // case of this is memory operands.
    4.58 -// Indirect is not included since its use is limited to Compare & Swap
    4.59  opclass memory( indirect, indOffset13, indIndex );
    4.60 +opclass indIndexMemory( indIndex );
    4.61  
    4.62  //----------PIPELINE-----------------------------------------------------------
    4.63  pipeline %{
    4.64 @@ -9666,84 +9629,179 @@
    4.65  
    4.66  instruct bytes_reverse_int(iRegI dst, stackSlotI src) %{
    4.67    match(Set dst (ReverseBytesI src));
    4.68 -  effect(DEF dst, USE src);
    4.69  
    4.70    // Op cost is artificially doubled to make sure that load or store
    4.71    // instructions are preferred over this one which requires a spill
    4.72    // onto a stack slot.
    4.73    ins_cost(2*DEFAULT_COST + MEMORY_REF_COST);
    4.74 -  size(8);
    4.75    format %{ "LDUWA  $src, $dst\t!asi=primary_little" %}
    4.76 -  opcode(Assembler::lduwa_op3);
    4.77 -  ins_encode( form3_mem_reg_little(src, dst) );
    4.78 +
    4.79 +  ins_encode %{
    4.80 +    __ set($src$$disp + STACK_BIAS, O7);
    4.81 +    __ lduwa($src$$base$$Register, O7, Assembler::ASI_PRIMARY_LITTLE, $dst$$Register);
    4.82 +  %}
    4.83    ins_pipe( iload_mem );
    4.84  %}
    4.85  
    4.86  instruct bytes_reverse_long(iRegL dst, stackSlotL src) %{
    4.87    match(Set dst (ReverseBytesL src));
    4.88 -  effect(DEF dst, USE src);
    4.89  
    4.90    // Op cost is artificially doubled to make sure that load or store
    4.91    // instructions are preferred over this one which requires a spill
    4.92    // onto a stack slot.
    4.93    ins_cost(2*DEFAULT_COST + MEMORY_REF_COST);
    4.94 -  size(8);
    4.95    format %{ "LDXA   $src, $dst\t!asi=primary_little" %}
    4.96  
    4.97 -  opcode(Assembler::ldxa_op3);
    4.98 -  ins_encode( form3_mem_reg_little(src, dst) );
    4.99 +  ins_encode %{
   4.100 +    __ set($src$$disp + STACK_BIAS, O7);
   4.101 +    __ ldxa($src$$base$$Register, O7, Assembler::ASI_PRIMARY_LITTLE, $dst$$Register);
   4.102 +  %}
   4.103    ins_pipe( iload_mem );
   4.104  %}
   4.105  
   4.106 +instruct bytes_reverse_unsigned_short(iRegI dst, stackSlotI src) %{
   4.107 +  match(Set dst (ReverseBytesUS src));
   4.108 +
   4.109 +  // Op cost is artificially doubled to make sure that load or store
   4.110 +  // instructions are preferred over this one which requires a spill
   4.111 +  // onto a stack slot.
   4.112 +  ins_cost(2*DEFAULT_COST + MEMORY_REF_COST);
   4.113 +  format %{ "LDUHA  $src, $dst\t!asi=primary_little\n\t" %}
   4.114 +
   4.115 +  ins_encode %{
   4.116 +    // the value was spilled as an int so bias the load
   4.117 +    __ set($src$$disp + STACK_BIAS + 2, O7);
   4.118 +    __ lduha($src$$base$$Register, O7, Assembler::ASI_PRIMARY_LITTLE, $dst$$Register);
   4.119 +  %}
   4.120 +  ins_pipe( iload_mem );
   4.121 +%}
   4.122 +
   4.123 +instruct bytes_reverse_short(iRegI dst, stackSlotI src) %{
   4.124 +  match(Set dst (ReverseBytesS src));
   4.125 +
   4.126 +  // Op cost is artificially doubled to make sure that load or store
   4.127 +  // instructions are preferred over this one which requires a spill
   4.128 +  // onto a stack slot.
   4.129 +  ins_cost(2*DEFAULT_COST + MEMORY_REF_COST);
   4.130 +  format %{ "LDSHA  $src, $dst\t!asi=primary_little\n\t" %}
   4.131 +
   4.132 +  ins_encode %{
   4.133 +    // the value was spilled as an int so bias the load
   4.134 +    __ set($src$$disp + STACK_BIAS + 2, O7);
   4.135 +    __ ldsha($src$$base$$Register, O7, Assembler::ASI_PRIMARY_LITTLE, $dst$$Register);
   4.136 +  %}
   4.137 +  ins_pipe( iload_mem );
   4.138 +%}
   4.139 +
   4.140  // Load Integer reversed byte order
   4.141 -instruct loadI_reversed(iRegI dst, memory src) %{
   4.142 +instruct loadI_reversed(iRegI dst, indIndexMemory src) %{
   4.143    match(Set dst (ReverseBytesI (LoadI src)));
   4.144  
   4.145    ins_cost(DEFAULT_COST + MEMORY_REF_COST);
   4.146 -  size(8);
   4.147 +  size(4);
   4.148    format %{ "LDUWA  $src, $dst\t!asi=primary_little" %}
   4.149  
   4.150 -  opcode(Assembler::lduwa_op3);
   4.151 -  ins_encode( form3_mem_reg_little( src, dst) );
   4.152 +  ins_encode %{
   4.153 +    __ lduwa($src$$base$$Register, $src$$index$$Register, Assembler::ASI_PRIMARY_LITTLE, $dst$$Register);
   4.154 +  %}
   4.155    ins_pipe(iload_mem);
   4.156  %}
   4.157  
   4.158  // Load Long - aligned and reversed
   4.159 -instruct loadL_reversed(iRegL dst, memory src) %{
   4.160 +instruct loadL_reversed(iRegL dst, indIndexMemory src) %{
   4.161    match(Set dst (ReverseBytesL (LoadL src)));
   4.162  
   4.163 -  ins_cost(DEFAULT_COST + MEMORY_REF_COST);
   4.164 -  size(8);
   4.165 +  ins_cost(MEMORY_REF_COST);
   4.166 +  size(4);
   4.167    format %{ "LDXA   $src, $dst\t!asi=primary_little" %}
   4.168  
   4.169 -  opcode(Assembler::ldxa_op3);
   4.170 -  ins_encode( form3_mem_reg_little( src, dst ) );
   4.171 +  ins_encode %{
   4.172 +    __ ldxa($src$$base$$Register, $src$$index$$Register, Assembler::ASI_PRIMARY_LITTLE, $dst$$Register);
   4.173 +  %}
   4.174    ins_pipe(iload_mem);
   4.175  %}
   4.176  
   4.177 +// Load unsigned short / char reversed byte order
   4.178 +instruct loadUS_reversed(iRegI dst, indIndexMemory src) %{
   4.179 +  match(Set dst (ReverseBytesUS (LoadUS src)));
   4.180 +
   4.181 +  ins_cost(MEMORY_REF_COST);
   4.182 +  size(4);
   4.183 +  format %{ "LDUHA  $src, $dst\t!asi=primary_little" %}
   4.184 +
   4.185 +  ins_encode %{
   4.186 +    __ lduha($src$$base$$Register, $src$$index$$Register, Assembler::ASI_PRIMARY_LITTLE, $dst$$Register);
   4.187 +  %}
   4.188 +  ins_pipe(iload_mem);
   4.189 +%}
   4.190 +
   4.191 +// Load short reversed byte order
   4.192 +instruct loadS_reversed(iRegI dst, indIndexMemory src) %{
   4.193 +  match(Set dst (ReverseBytesS (LoadS src)));
   4.194 +
   4.195 +  ins_cost(MEMORY_REF_COST);
   4.196 +  size(4);
   4.197 +  format %{ "LDSHA  $src, $dst\t!asi=primary_little" %}
   4.198 +
   4.199 +  ins_encode %{
   4.200 +    __ ldsha($src$$base$$Register, $src$$index$$Register, Assembler::ASI_PRIMARY_LITTLE, $dst$$Register);
   4.201 +  %}
   4.202 +  ins_pipe(iload_mem);
   4.203 +%}
   4.204 +
   4.205  // Store Integer reversed byte order
   4.206 -instruct storeI_reversed(memory dst, iRegI src) %{
   4.207 +instruct storeI_reversed(indIndexMemory dst, iRegI src) %{
   4.208    match(Set dst (StoreI dst (ReverseBytesI src)));
   4.209  
   4.210    ins_cost(MEMORY_REF_COST);
   4.211 -  size(8);
   4.212 +  size(4);
   4.213    format %{ "STWA   $src, $dst\t!asi=primary_little" %}
   4.214  
   4.215 -  opcode(Assembler::stwa_op3);
   4.216 -  ins_encode( form3_mem_reg_little( dst, src) );
   4.217 +  ins_encode %{
   4.218 +    __ stwa($src$$Register, $dst$$base$$Register, $dst$$index$$Register, Assembler::ASI_PRIMARY_LITTLE);
   4.219 +  %}
   4.220    ins_pipe(istore_mem_reg);
   4.221  %}
   4.222  
   4.223  // Store Long reversed byte order
   4.224 -instruct storeL_reversed(memory dst, iRegL src) %{
   4.225 +instruct storeL_reversed(indIndexMemory dst, iRegL src) %{
   4.226    match(Set dst (StoreL dst (ReverseBytesL src)));
   4.227  
   4.228    ins_cost(MEMORY_REF_COST);
   4.229 -  size(8);
   4.230 +  size(4);
   4.231    format %{ "STXA   $src, $dst\t!asi=primary_little" %}
   4.232  
   4.233 -  opcode(Assembler::stxa_op3);
   4.234 -  ins_encode( form3_mem_reg_little( dst, src) );
   4.235 +  ins_encode %{
   4.236 +    __ stxa($src$$Register, $dst$$base$$Register, $dst$$index$$Register, Assembler::ASI_PRIMARY_LITTLE);
   4.237 +  %}
   4.238 +  ins_pipe(istore_mem_reg);
   4.239 +%}
   4.240 +
   4.241 +// Store unsighed short/char reversed byte order
   4.242 +instruct storeUS_reversed(indIndexMemory dst, iRegI src) %{
   4.243 +  match(Set dst (StoreC dst (ReverseBytesUS src)));
   4.244 +
   4.245 +  ins_cost(MEMORY_REF_COST);
   4.246 +  size(4);
   4.247 +  format %{ "STHA   $src, $dst\t!asi=primary_little" %}
   4.248 +
   4.249 +  ins_encode %{
   4.250 +    __ stha($src$$Register, $dst$$base$$Register, $dst$$index$$Register, Assembler::ASI_PRIMARY_LITTLE);
   4.251 +  %}
   4.252 +  ins_pipe(istore_mem_reg);
   4.253 +%}
   4.254 +
   4.255 +// Store short reversed byte order
   4.256 +instruct storeS_reversed(indIndexMemory dst, iRegI src) %{
   4.257 +  match(Set dst (StoreC dst (ReverseBytesS src)));
   4.258 +
   4.259 +  ins_cost(MEMORY_REF_COST);
   4.260 +  size(4);
   4.261 +  format %{ "STHA   $src, $dst\t!asi=primary_little" %}
   4.262 +
   4.263 +  ins_encode %{
   4.264 +    __ stha($src$$Register, $dst$$base$$Register, $dst$$index$$Register, Assembler::ASI_PRIMARY_LITTLE);
   4.265 +  %}
   4.266    ins_pipe(istore_mem_reg);
   4.267  %}
   4.268  
     5.1 --- a/src/cpu/x86/vm/x86_32.ad	Tue Apr 20 13:26:33 2010 -0700
     5.2 +++ b/src/cpu/x86/vm/x86_32.ad	Mon Apr 26 11:27:21 2010 -0700
     5.3 @@ -1,5 +1,5 @@
     5.4  //
     5.5 -// Copyright 1997-2009 Sun Microsystems, Inc.  All Rights Reserved.
     5.6 +// Copyright 1997-2010 Sun Microsystems, Inc.  All Rights Reserved.
     5.7  // DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
     5.8  //
     5.9  // This code is free software; you can redistribute it and/or modify it
    5.10 @@ -6272,6 +6272,30 @@
    5.11    ins_pipe( ialu_reg_reg);
    5.12  %}
    5.13  
    5.14 +instruct bytes_reverse_unsigned_short(eRegI dst) %{
    5.15 +  match(Set dst (ReverseBytesUS dst));
    5.16 +
    5.17 +  format %{ "BSWAP  $dst\n\t" 
    5.18 +            "SHR    $dst,16\n\t" %}
    5.19 +  ins_encode %{
    5.20 +    __ bswapl($dst$$Register);
    5.21 +    __ shrl($dst$$Register, 16); 
    5.22 +  %}
    5.23 +  ins_pipe( ialu_reg );
    5.24 +%}
    5.25 +
    5.26 +instruct bytes_reverse_short(eRegI dst) %{
    5.27 +  match(Set dst (ReverseBytesS dst));
    5.28 +
    5.29 +  format %{ "BSWAP  $dst\n\t" 
    5.30 +            "SAR    $dst,16\n\t" %}
    5.31 +  ins_encode %{
    5.32 +    __ bswapl($dst$$Register);
    5.33 +    __ sarl($dst$$Register, 16); 
    5.34 +  %}
    5.35 +  ins_pipe( ialu_reg );
    5.36 +%}
    5.37 +
    5.38  
    5.39  //---------- Zeros Count Instructions ------------------------------------------
    5.40  
     6.1 --- a/src/cpu/x86/vm/x86_64.ad	Tue Apr 20 13:26:33 2010 -0700
     6.2 +++ b/src/cpu/x86/vm/x86_64.ad	Mon Apr 26 11:27:21 2010 -0700
     6.3 @@ -1,5 +1,5 @@
     6.4  //
     6.5 -// Copyright 2003-2009 Sun Microsystems, Inc.  All Rights Reserved.
     6.6 +// Copyright 2003-2010 Sun Microsystems, Inc.  All Rights Reserved.
     6.7  // DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
     6.8  //
     6.9  // This code is free software; you can redistribute it and/or modify it
    6.10 @@ -7371,6 +7371,30 @@
    6.11    ins_pipe( ialu_reg);
    6.12  %}
    6.13  
    6.14 +instruct bytes_reverse_unsigned_short(rRegI dst) %{
    6.15 +  match(Set dst (ReverseBytesUS dst));
    6.16 +
    6.17 +  format %{ "bswapl  $dst\n\t" 
    6.18 +            "shrl    $dst,16\n\t" %}
    6.19 +  ins_encode %{
    6.20 +    __ bswapl($dst$$Register);
    6.21 +    __ shrl($dst$$Register, 16); 
    6.22 +  %}
    6.23 +  ins_pipe( ialu_reg );
    6.24 +%}
    6.25 +
    6.26 +instruct bytes_reverse_short(rRegI dst) %{
    6.27 +  match(Set dst (ReverseBytesS dst));
    6.28 +
    6.29 +  format %{ "bswapl  $dst\n\t" 
    6.30 +            "sar     $dst,16\n\t" %}
    6.31 +  ins_encode %{
    6.32 +    __ bswapl($dst$$Register);
    6.33 +    __ sarl($dst$$Register, 16); 
    6.34 +  %}
    6.35 +  ins_pipe( ialu_reg );
    6.36 +%}
    6.37 +
    6.38  instruct loadI_reversed(rRegI dst, memory src) %{
    6.39    match(Set dst (ReverseBytesI (LoadI src)));
    6.40  
     7.1 --- a/src/share/vm/adlc/formssel.cpp	Tue Apr 20 13:26:33 2010 -0700
     7.2 +++ b/src/share/vm/adlc/formssel.cpp	Mon Apr 26 11:27:21 2010 -0700
     7.3 @@ -1,5 +1,5 @@
     7.4  /*
     7.5 - * Copyright 1998-2009 Sun Microsystems, Inc.  All Rights Reserved.
     7.6 + * Copyright 1998-2010 Sun Microsystems, Inc.  All Rights Reserved.
     7.7   * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
     7.8   *
     7.9   * This code is free software; you can redistribute it and/or modify it
    7.10 @@ -3861,6 +3861,8 @@
    7.11          strcmp(opType,"RoundFloat")==0 ||
    7.12          strcmp(opType,"ReverseBytesI")==0 ||
    7.13          strcmp(opType,"ReverseBytesL")==0 ||
    7.14 +        strcmp(opType,"ReverseBytesUS")==0 ||
    7.15 +        strcmp(opType,"ReverseBytesS")==0 ||
    7.16          strcmp(opType,"Replicate16B")==0 ||
    7.17          strcmp(opType,"Replicate8B")==0 ||
    7.18          strcmp(opType,"Replicate4B")==0 ||
     8.1 --- a/src/share/vm/classfile/vmSymbols.hpp	Tue Apr 20 13:26:33 2010 -0700
     8.2 +++ b/src/share/vm/classfile/vmSymbols.hpp	Mon Apr 26 11:27:21 2010 -0700
     8.3 @@ -1,5 +1,5 @@
     8.4  /*
     8.5 - * Copyright 1997-2009 Sun Microsystems, Inc.  All Rights Reserved.
     8.6 + * Copyright 1997-2010 Sun Microsystems, Inc.  All Rights Reserved.
     8.7   * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
     8.8   *
     8.9   * This code is free software; you can redistribute it and/or modify it
    8.10 @@ -357,6 +357,8 @@
    8.11    template(void_double_signature,                     "()D")                                      \
    8.12    template(int_void_signature,                        "(I)V")                                     \
    8.13    template(int_int_signature,                         "(I)I")                                     \
    8.14 +  template(char_char_signature,                       "(C)C")                                     \
    8.15 +  template(short_short_signature,                     "(S)S")                                     \
    8.16    template(int_bool_signature,                        "(I)Z")                                     \
    8.17    template(float_int_signature,                       "(F)I")                                     \
    8.18    template(double_long_signature,                     "(D)J")                                     \
    8.19 @@ -585,6 +587,10 @@
    8.20     do_name(     reverseBytes_name,                               "reverseBytes")                                        \
    8.21    do_intrinsic(_reverseBytes_l,           java_lang_Long,         reverseBytes_name,        long_long_signature, F_S)   \
    8.22      /*  (symbol reverseBytes_name defined above) */                                                                     \
    8.23 +  do_intrinsic(_reverseBytes_c,           java_lang_Character,    reverseBytes_name,        char_char_signature, F_S)   \
    8.24 +    /*  (symbol reverseBytes_name defined above) */                                                                     \
    8.25 +  do_intrinsic(_reverseBytes_s,           java_lang_Short,        reverseBytes_name,        short_short_signature, F_S) \
    8.26 +    /*  (symbol reverseBytes_name defined above) */                                                                     \
    8.27                                                                                                                          \
    8.28    do_intrinsic(_identityHashCode,         java_lang_System,       identityHashCode_name, object_int_signature,   F_S)   \
    8.29     do_name(     identityHashCode_name,                           "identityHashCode")                                    \
     9.1 --- a/src/share/vm/opto/classes.hpp	Tue Apr 20 13:26:33 2010 -0700
     9.2 +++ b/src/share/vm/opto/classes.hpp	Mon Apr 26 11:27:21 2010 -0700
     9.3 @@ -1,5 +1,5 @@
     9.4  /*
     9.5 - * Copyright 1997-2009 Sun Microsystems, Inc.  All Rights Reserved.
     9.6 + * Copyright 1997-2010 Sun Microsystems, Inc.  All Rights Reserved.
     9.7   * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
     9.8   *
     9.9   * This code is free software; you can redistribute it and/or modify it
    9.10 @@ -44,6 +44,8 @@
    9.11  macro(BoxLock)
    9.12  macro(ReverseBytesI)
    9.13  macro(ReverseBytesL)
    9.14 +macro(ReverseBytesUS)
    9.15 +macro(ReverseBytesS)
    9.16  macro(CProj)
    9.17  macro(CallDynamicJava)
    9.18  macro(CallJava)
    10.1 --- a/src/share/vm/opto/library_call.cpp	Tue Apr 20 13:26:33 2010 -0700
    10.2 +++ b/src/share/vm/opto/library_call.cpp	Mon Apr 26 11:27:21 2010 -0700
    10.3 @@ -636,6 +636,8 @@
    10.4  
    10.5    case vmIntrinsics::_reverseBytes_i:
    10.6    case vmIntrinsics::_reverseBytes_l:
    10.7 +  case vmIntrinsics::_reverseBytes_s:
    10.8 +  case vmIntrinsics::_reverseBytes_c:
    10.9      return inline_reverseBytes((vmIntrinsics::ID) intrinsic_id());
   10.10  
   10.11    case vmIntrinsics::_get_AtomicLong:
   10.12 @@ -2010,13 +2012,19 @@
   10.13    return true;
   10.14  }
   10.15  
   10.16 -//----------------------------inline_reverseBytes_int/long-------------------
   10.17 +//----------------------------inline_reverseBytes_int/long/char/short-------------------
   10.18  // inline Integer.reverseBytes(int)
   10.19  // inline Long.reverseBytes(long)
   10.20 +// inline Character.reverseBytes(char)
   10.21 +// inline Short.reverseBytes(short)
   10.22  bool LibraryCallKit::inline_reverseBytes(vmIntrinsics::ID id) {
   10.23 -  assert(id == vmIntrinsics::_reverseBytes_i || id == vmIntrinsics::_reverseBytes_l, "not reverse Bytes");
   10.24 -  if (id == vmIntrinsics::_reverseBytes_i && !Matcher::has_match_rule(Op_ReverseBytesI)) return false;
   10.25 -  if (id == vmIntrinsics::_reverseBytes_l && !Matcher::has_match_rule(Op_ReverseBytesL)) return false;
   10.26 +  assert(id == vmIntrinsics::_reverseBytes_i || id == vmIntrinsics::_reverseBytes_l ||
   10.27 +         id == vmIntrinsics::_reverseBytes_c || id == vmIntrinsics::_reverseBytes_s,
   10.28 +         "not reverse Bytes");
   10.29 +  if (id == vmIntrinsics::_reverseBytes_i && !Matcher::has_match_rule(Op_ReverseBytesI))  return false;
   10.30 +  if (id == vmIntrinsics::_reverseBytes_l && !Matcher::has_match_rule(Op_ReverseBytesL))  return false;
   10.31 +  if (id == vmIntrinsics::_reverseBytes_c && !Matcher::has_match_rule(Op_ReverseBytesUS)) return false;
   10.32 +  if (id == vmIntrinsics::_reverseBytes_s && !Matcher::has_match_rule(Op_ReverseBytesS))  return false;
   10.33    _sp += arg_size();        // restore stack pointer
   10.34    switch (id) {
   10.35    case vmIntrinsics::_reverseBytes_i:
   10.36 @@ -2025,6 +2033,12 @@
   10.37    case vmIntrinsics::_reverseBytes_l:
   10.38      push_pair(_gvn.transform(new (C, 2) ReverseBytesLNode(0, pop_pair())));
   10.39      break;
   10.40 +  case vmIntrinsics::_reverseBytes_c:
   10.41 +    push(_gvn.transform(new (C, 2) ReverseBytesUSNode(0, pop())));
   10.42 +    break;
   10.43 +  case vmIntrinsics::_reverseBytes_s:
   10.44 +    push(_gvn.transform(new (C, 2) ReverseBytesSNode(0, pop())));
   10.45 +    break;
   10.46    default:
   10.47      ;
   10.48    }
    11.1 --- a/src/share/vm/opto/subnode.hpp	Tue Apr 20 13:26:33 2010 -0700
    11.2 +++ b/src/share/vm/opto/subnode.hpp	Mon Apr 26 11:27:21 2010 -0700
    11.3 @@ -1,5 +1,5 @@
    11.4  /*
    11.5 - * Copyright 1997-2008 Sun Microsystems, Inc.  All Rights Reserved.
    11.6 + * Copyright 1997-2010 Sun Microsystems, Inc.  All Rights Reserved.
    11.7   * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    11.8   *
    11.9   * This code is free software; you can redistribute it and/or modify it
   11.10 @@ -509,3 +509,23 @@
   11.11    const Type *bottom_type() const { return TypeLong::LONG; }
   11.12    virtual uint ideal_reg() const { return Op_RegL; }
   11.13  };
   11.14 +
   11.15 +//-------------------------------ReverseBytesUSNode--------------------------------
   11.16 +// reverse bytes of an unsigned short / char
   11.17 +class ReverseBytesUSNode : public Node {
   11.18 +public:
   11.19 +  ReverseBytesUSNode(Node *c, Node *in1) : Node(c, in1) {}
   11.20 +  virtual int Opcode() const;
   11.21 +  const Type *bottom_type() const { return TypeInt::CHAR; }
   11.22 +  virtual uint ideal_reg() const { return Op_RegI; }
   11.23 +};
   11.24 +
   11.25 +//-------------------------------ReverseBytesSNode--------------------------------
   11.26 +// reverse bytes of a short
   11.27 +class ReverseBytesSNode : public Node {
   11.28 +public:
   11.29 +  ReverseBytesSNode(Node *c, Node *in1) : Node(c, in1) {}
   11.30 +  virtual int Opcode() const;
   11.31 +  const Type *bottom_type() const { return TypeInt::SHORT; }
   11.32 +  virtual uint ideal_reg() const { return Op_RegI; }
   11.33 +};
    12.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    12.2 +++ b/test/compiler/6431242/Test.java	Mon Apr 26 11:27:21 2010 -0700
    12.3 @@ -0,0 +1,176 @@
    12.4 +/*
    12.5 + * Copyright 2006 Sun Microsystems, Inc.  All Rights Reserved.
    12.6 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    12.7 + *
    12.8 + * This code is free software; you can redistribute it and/or modify it
    12.9 + * under the terms of the GNU General Public License version 2 only, as
   12.10 + * published by the Free Software Foundation.
   12.11 + *
   12.12 + * This code is distributed in the hope that it will be useful, but WITHOUT
   12.13 + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
   12.14 + * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
   12.15 + * version 2 for more details (a copy is included in the LICENSE file that
   12.16 + * accompanied this code).
   12.17 + *
   12.18 + * You should have received a copy of the GNU General Public License version
   12.19 + * 2 along with this work; if not, write to the Free Software Foundation,
   12.20 + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
   12.21 + *
   12.22 + * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
   12.23 + * CA 95054 USA or visit www.sun.com if you need additional information or
   12.24 + * have any questions.
   12.25 + *
   12.26 + */
   12.27 +
   12.28 +/*
   12.29 + * @test
   12.30 + * @bug 6431242
   12.31 + * @run main/othervm -server -XX:+PrintCompilation Test
   12.32 + */
   12.33 +
   12.34 +public class Test{
   12.35 +
   12.36 +  int    _len      = 8;
   12.37 +  int[]  _arr_i    = new int[_len];
   12.38 +  long[] _arr_l    = new long[_len];
   12.39 +
   12.40 +  int[]  _arr_i_cp = new int [_len];
   12.41 +  long[] _arr_l_cp = new long [_len];
   12.42 +
   12.43 +  int _k     = 0x12345678;
   12.44 +  int _j     = 0;
   12.45 +  int _ir    = 0x78563412;
   12.46 +  int _ir1   = 0x78563413;
   12.47 +  int _ir2   = 0x79563412;
   12.48 +
   12.49 +  long _m    = 0x123456789abcdef0L;
   12.50 +  long _l    = 0L;
   12.51 +  long _lr   = 0xf0debc9a78563412L;
   12.52 +  long _lr1  = 0xf0debc9a78563413L;
   12.53 +  long _lr2  = 0xf1debc9a78563412L;
   12.54 +
   12.55 +  void init() {
   12.56 +    for (int i=0; i<_arr_i.length; i++) {
   12.57 +      _arr_i[i] = _k;
   12.58 +      _arr_l[i] = _m;
   12.59 +    }
   12.60 +  }
   12.61 +
   12.62 +  public int test_int_reversed(int i) {
   12.63 +    return Integer.reverseBytes(i);
   12.64 +  }
   12.65 +
   12.66 +  public long test_long_reversed(long i) {
   12.67 +    return Long.reverseBytes(i);
   12.68 +  }
   12.69 +
   12.70 +  public void test_copy_ints(int[] dst, int[] src) {
   12.71 +    for(int i=0; i<src.length; i++) {
   12.72 +      dst[i] = Integer.reverseBytes(src[i]);
   12.73 +    }
   12.74 +  }
   12.75 +
   12.76 +  public void test_copy_ints_reversed(int[] dst, int[] src) {
   12.77 +    for (int i=0; i<src.length; i++) {
   12.78 +      dst[i] = 1 + Integer.reverseBytes(src[i]);
   12.79 +    }
   12.80 +  }
   12.81 +
   12.82 +  public void test_copy_ints_store_reversed(int[] dst, int[] src) {
   12.83 +    for(int i=0; i<src.length; i++) {
   12.84 +      dst[i] = Integer.reverseBytes(1 + src[i]);
   12.85 +    }
   12.86 +  }
   12.87 +
   12.88 +  public void test_copy_longs(long[] dst, long[] src) {
   12.89 +    for(int i=0; i<src.length; i++) {
   12.90 +      dst[i] = Long.reverseBytes(src[i]);
   12.91 +    }
   12.92 +  }
   12.93 +
   12.94 +  public void test_copy_longs_reversed(long[] dst, long[] src) {
   12.95 +    for (int i=0; i<src.length; i++) {
   12.96 +      dst[i] = 1 + Long.reverseBytes(src[i]);
   12.97 +    }
   12.98 +  }
   12.99 +
  12.100 +  public void test_copy_longs_store_reversed(long[] dst, long[] src) {
  12.101 +    for(int i=0; i<src.length; i++) {
  12.102 +      dst[i] = Long.reverseBytes(1 + src[i]);
  12.103 +    }
  12.104 +  }
  12.105 +
  12.106 +  public void test() throws Exception {
  12.107 +    int up_limit=90000;
  12.108 +
  12.109 +
  12.110 +    //test single
  12.111 +
  12.112 +    for (int loop=0; loop<up_limit; loop++) {
  12.113 +      _j = test_int_reversed(_k);
  12.114 +      if (_j != _ir ) {
  12.115 +        throw new Exception("Interger.reverseBytes failed " + _j + " iter " + loop);
  12.116 +      }
  12.117 +      _l = test_long_reversed(_m);
  12.118 +      if (_l != _lr ) {
  12.119 +        throw new Exception("Long.reverseBytes failed " + _l + " iter " + loop);
  12.120 +      }
  12.121 +    }
  12.122 +
  12.123 +    // test scalar load/store
  12.124 +    for (int loop=0; loop<up_limit; loop++) {
  12.125 +
  12.126 +      test_copy_ints(_arr_i_cp, _arr_i);
  12.127 +      for (int j=0; j< _arr_i.length; j++) {
  12.128 +        if (_arr_i_cp[j] != _ir) {
  12.129 +          throw new Exception("Interger.reverseBytes failed test_copy_ints iter " + loop);
  12.130 +        }
  12.131 +      }
  12.132 +
  12.133 +      test_copy_ints_reversed(_arr_i_cp, _arr_i);
  12.134 +      for (int j=0; j< _arr_i.length; j++) {
  12.135 +        if (_arr_i_cp[j] != _ir1) {
  12.136 +          throw new Exception("Interger.reverseBytes failed test_copy_ints_reversed iter " + loop);
  12.137 +        }
  12.138 +      }
  12.139 +      test_copy_ints_store_reversed(_arr_i_cp, _arr_i);
  12.140 +      for (int j=0; j< _arr_i.length; j++) {
  12.141 +        if (_arr_i_cp[j] != _ir2) {
  12.142 +          throw new Exception("Interger.reverseBytes failed test_copy_ints_store_reversed iter " + loop);
  12.143 +        }
  12.144 +      }
  12.145 +
  12.146 +      test_copy_longs(_arr_l_cp, _arr_l);
  12.147 +      for (int j=0; j< _arr_i.length; j++) {
  12.148 +        if (_arr_l_cp[j] != _lr) {
  12.149 +          throw new Exception("Long.reverseBytes failed test_copy_longs iter " + loop);
  12.150 +        }
  12.151 +      }
  12.152 +      test_copy_longs_reversed(_arr_l_cp, _arr_l);
  12.153 +      for (int j=0; j< _arr_i.length; j++) {
  12.154 +        if (_arr_l_cp[j] != _lr1) {
  12.155 +          throw new Exception("Long.reverseBytes failed test_copy_longs_reversed iter " + loop);
  12.156 +        }
  12.157 +      }
  12.158 +      test_copy_longs_store_reversed(_arr_l_cp, _arr_l);
  12.159 +      for (int j=0; j< _arr_i.length; j++) {
  12.160 +        if (_arr_l_cp[j] != _lr2) {
  12.161 +          throw new Exception("Long.reverseBytes failed test_copy_longs_store_reversed iter " + loop);
  12.162 +        }
  12.163 +      }
  12.164 +
  12.165 +    }
  12.166 +  }
  12.167 +
  12.168 +  public static void main(String args[]) {
  12.169 +    try {
  12.170 +      Test t = new Test();
  12.171 +      t.init();
  12.172 +      t.test();
  12.173 +      System.out.println("Passed");
  12.174 +    }catch (Exception e) {
  12.175 +      e.printStackTrace();
  12.176 +      System.out.println("Failed");
  12.177 +    }
  12.178 +  }
  12.179 +}
    13.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    13.2 +++ b/test/compiler/6946040/TestCharShortByteSwap.java	Mon Apr 26 11:27:21 2010 -0700
    13.3 @@ -0,0 +1,88 @@
    13.4 +/*
    13.5 + * Copyright 2010 Google, Inc.  All Rights Reserved.
    13.6 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    13.7 + *
    13.8 + * This code is free software; you can redistribute it and/or modify it
    13.9 + * under the terms of the GNU General Public License version 2 only, as
   13.10 + * published by the Free Software Foundation.
   13.11 + *
   13.12 + * This code is distributed in the hope that it will be useful, but WITHOUT
   13.13 + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
   13.14 + * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
   13.15 + * version 2 for more details (a copy is included in the LICENSE file that
   13.16 + * accompanied this code).
   13.17 + *
   13.18 + * You should have received a copy of the GNU General Public License version
   13.19 + * 2 along with this work; if not, write to the Free Software Foundation,
   13.20 + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
   13.21 + *
   13.22 + * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
   13.23 + * CA 95054 USA or visit www.sun.com if you need additional information or
   13.24 + * have any questions.
   13.25 + *
   13.26 + */
   13.27 +
   13.28 +/*
   13.29 + * @test
   13.30 + * @bug 6946040
   13.31 + * @summary Tests Character/Short.reverseBytes and their intrinsics implementation in the server compiler
   13.32 + * @run main/othervm -Xbatch -server -XX:CompileOnly=.testChar,.testShort TestCharShortByteSwap
   13.33 + */
   13.34 +
   13.35 +// This test must run without any command line arguments.
   13.36 +
   13.37 +public class TestCharShortByteSwap {
   13.38 +
   13.39 +  private static short initShort(String[] args, short v) {
   13.40 +    if (args.length > 0) {
   13.41 +      try {
   13.42 +        return (short) Integer.valueOf(args[0]).intValue();
   13.43 +      } catch (NumberFormatException e) { }
   13.44 +    }
   13.45 +    return v;
   13.46 +  }
   13.47 +
   13.48 +  private static char initChar(String[] args, char v) {
   13.49 +    if (args.length > 0) {
   13.50 +      try {
   13.51 +        return (char) Integer.valueOf(args[0]).intValue();
   13.52 +      } catch (NumberFormatException e) { }
   13.53 +    }
   13.54 +    return v;
   13.55 +  }
   13.56 +
   13.57 +  private static void testChar(char a, char b) {
   13.58 +    if (a != Character.reverseBytes(b)) {
   13.59 +      throw new RuntimeException("FAIL: " + (int)a + " != Character.reverseBytes(" + (int)b + ")");
   13.60 +    }
   13.61 +    if (b != Character.reverseBytes(a)) {
   13.62 +      throw new RuntimeException("FAIL: " + (int)b + " != Character.reverseBytes(" + (int)a + ")");
   13.63 +    }
   13.64 +  }
   13.65 +
   13.66 +  private static void testShort(short a, short b) {
   13.67 +    if (a != Short.reverseBytes(b)) {
   13.68 +      throw new RuntimeException("FAIL: " + (int)a + " != Short.reverseBytes(" + (int)b + ")");
   13.69 +    }
   13.70 +    if (b != Short.reverseBytes(a)) {
   13.71 +      throw new RuntimeException("FAIL: " + (int)b + " != Short.reverseBytes(" + (int)a + ")");
   13.72 +    }
   13.73 +  }
   13.74 +
   13.75 +  public static void main(String[] args) {
   13.76 +    for (int i = 0; i < 100000; ++i) { // Trigger compilation
   13.77 +      char c1 = initChar(args, (char) 0x0123);
   13.78 +      char c2 = initChar(args, (char) 0x2301);
   13.79 +      char c3 = initChar(args, (char) 0xaabb);
   13.80 +      char c4 = initChar(args, (char) 0xbbaa);
   13.81 +      short s1 = initShort(args, (short) 0x0123);
   13.82 +      short s2 = initShort(args, (short) 0x2301);
   13.83 +      short s3 = initShort(args, (short) 0xaabb);
   13.84 +      short s4 = initShort(args, (short) 0xbbaa);
   13.85 +      testChar(c1, c2);
   13.86 +      testChar(c3, c4);
   13.87 +      testShort(s1, s2);
   13.88 +      testShort(s3, s4);
   13.89 +    }
   13.90 +  }
   13.91 +}

mercurial