hotspot/src/cpu/x86/vm/templateInterpreterGenerator_x86_32.cpp
changeset 34651 07b1cc0f6040
parent 33161 81170a43bb2a
child 35214 d86005e0b4c2
equal deleted inserted replaced
34648:b7ea5d095ef5 34651:07b1cc0f6040
       
     1 /*
       
     2  * Copyright (c) 1997, 2015, Oracle and/or its affiliates. All rights reserved.
       
     3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
       
     4  *
       
     5  * This code is free software; you can redistribute it and/or modify it
       
     6  * under the terms of the GNU General Public License version 2 only, as
       
     7  * published by the Free Software Foundation.
       
     8  *
       
     9  * This code is distributed in the hope that it will be useful, but WITHOUT
       
    10  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
       
    11  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
       
    12  * version 2 for more details (a copy is included in the LICENSE file that
       
    13  * accompanied this code).
       
    14  *
       
    15  * You should have received a copy of the GNU General Public License version
       
    16  * 2 along with this work; if not, write to the Free Software Foundation,
       
    17  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
       
    18  *
       
    19  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
       
    20  * or visit www.oracle.com if you need additional information or have any
       
    21  * questions.
       
    22  *
       
    23  */
       
    24 
       
    25 #include "precompiled.hpp"
       
    26 #include "asm/macroAssembler.hpp"
       
    27 #include "interpreter/interpreter.hpp"
       
    28 #include "interpreter/interpreterGenerator.hpp"
       
    29 #include "runtime/arguments.hpp"
       
    30 
       
    31 #define __ _masm->
       
    32 
       
    33 
       
    34 #ifndef CC_INTERP
       
    35 
       
    36 /**
       
    37  * Method entry for static native methods:
       
    38  *   int java.util.zip.CRC32.update(int crc, int b)
       
    39  */
       
    40 address InterpreterGenerator::generate_CRC32_update_entry() {
       
    41   if (UseCRC32Intrinsics) {
       
    42     address entry = __ pc();
       
    43 
       
    44     // rbx: Method*
       
    45     // rsi: senderSP must preserved for slow path, set SP to it on fast path
       
    46     // rdx: scratch
       
    47     // rdi: scratch
       
    48 
       
    49     Label slow_path;
       
    50     // If we need a safepoint check, generate full interpreter entry.
       
    51     ExternalAddress state(SafepointSynchronize::address_of_state());
       
    52     __ cmp32(ExternalAddress(SafepointSynchronize::address_of_state()),
       
    53              SafepointSynchronize::_not_synchronized);
       
    54     __ jcc(Assembler::notEqual, slow_path);
       
    55 
       
    56     // We don't generate local frame and don't align stack because
       
    57     // we call stub code and there is no safepoint on this path.
       
    58 
       
    59     // Load parameters
       
    60     const Register crc = rax;  // crc
       
    61     const Register val = rdx;  // source java byte value
       
    62     const Register tbl = rdi;  // scratch
       
    63 
       
    64     // Arguments are reversed on java expression stack
       
    65     __ movl(val, Address(rsp,   wordSize)); // byte value
       
    66     __ movl(crc, Address(rsp, 2*wordSize)); // Initial CRC
       
    67 
       
    68     __ lea(tbl, ExternalAddress(StubRoutines::crc_table_addr()));
       
    69     __ notl(crc); // ~crc
       
    70     __ update_byte_crc32(crc, val, tbl);
       
    71     __ notl(crc); // ~crc
       
    72     // result in rax
       
    73 
       
    74     // _areturn
       
    75     __ pop(rdi);                // get return address
       
    76     __ mov(rsp, rsi);           // set sp to sender sp
       
    77     __ jmp(rdi);
       
    78 
       
    79     // generate a vanilla native entry as the slow path
       
    80     __ bind(slow_path);
       
    81     __ jump_to_entry(Interpreter::entry_for_kind(Interpreter::native));
       
    82     return entry;
       
    83   }
       
    84   return NULL;
       
    85 }
       
    86 
       
    87 /**
       
    88  * Method entry for static native methods:
       
    89  *   int java.util.zip.CRC32.updateBytes(int crc, byte[] b, int off, int len)
       
    90  *   int java.util.zip.CRC32.updateByteBuffer(int crc, long buf, int off, int len)
       
    91  */
       
    92 address InterpreterGenerator::generate_CRC32_updateBytes_entry(AbstractInterpreter::MethodKind kind) {
       
    93   if (UseCRC32Intrinsics) {
       
    94     address entry = __ pc();
       
    95 
       
    96     // rbx,: Method*
       
    97     // rsi: senderSP must preserved for slow path, set SP to it on fast path
       
    98     // rdx: scratch
       
    99     // rdi: scratch
       
   100 
       
   101     Label slow_path;
       
   102     // If we need a safepoint check, generate full interpreter entry.
       
   103     ExternalAddress state(SafepointSynchronize::address_of_state());
       
   104     __ cmp32(ExternalAddress(SafepointSynchronize::address_of_state()),
       
   105              SafepointSynchronize::_not_synchronized);
       
   106     __ jcc(Assembler::notEqual, slow_path);
       
   107 
       
   108     // We don't generate local frame and don't align stack because
       
   109     // we call stub code and there is no safepoint on this path.
       
   110 
       
   111     // Load parameters
       
   112     const Register crc = rax;  // crc
       
   113     const Register buf = rdx;  // source java byte array address
       
   114     const Register len = rdi;  // length
       
   115 
       
   116     // value              x86_32
       
   117     // interp. arg ptr    ESP + 4
       
   118     // int java.util.zip.CRC32.updateBytes(int crc, byte[] b, int off, int len)
       
   119     //                                         3           2      1        0
       
   120     // int java.util.zip.CRC32.updateByteBuffer(int crc, long buf, int off, int len)
       
   121     //                                              4         2,3      1        0
       
   122 
       
   123     // Arguments are reversed on java expression stack
       
   124     __ movl(len,   Address(rsp,   4 + 0)); // Length
       
   125     // Calculate address of start element
       
   126     if (kind == Interpreter::java_util_zip_CRC32_updateByteBuffer) {
       
   127       __ movptr(buf, Address(rsp, 4 + 2 * wordSize)); // long buf
       
   128       __ addptr(buf, Address(rsp, 4 + 1 * wordSize)); // + offset
       
   129       __ movl(crc,   Address(rsp, 4 + 4 * wordSize)); // Initial CRC
       
   130     } else {
       
   131       __ movptr(buf, Address(rsp, 4 + 2 * wordSize)); // byte[] array
       
   132       __ addptr(buf, arrayOopDesc::base_offset_in_bytes(T_BYTE)); // + header size
       
   133       __ addptr(buf, Address(rsp, 4 + 1 * wordSize)); // + offset
       
   134       __ movl(crc,   Address(rsp, 4 + 3 * wordSize)); // Initial CRC
       
   135     }
       
   136 
       
   137     __ super_call_VM_leaf(CAST_FROM_FN_PTR(address, StubRoutines::updateBytesCRC32()), crc, buf, len);
       
   138     // result in rax
       
   139 
       
   140     // _areturn
       
   141     __ pop(rdi);                // get return address
       
   142     __ mov(rsp, rsi);           // set sp to sender sp
       
   143     __ jmp(rdi);
       
   144 
       
   145     // generate a vanilla native entry as the slow path
       
   146     __ bind(slow_path);
       
   147     __ jump_to_entry(Interpreter::entry_for_kind(Interpreter::native));
       
   148     return entry;
       
   149   }
       
   150   return NULL;
       
   151 }
       
   152 
       
   153 /**
       
   154 * Method entry for static native methods:
       
   155 *   int java.util.zip.CRC32C.updateBytes(int crc, byte[] b, int off, int end)
       
   156 *   int java.util.zip.CRC32C.updateByteBuffer(int crc, long address, int off, int end)
       
   157 */
       
   158 address InterpreterGenerator::generate_CRC32C_updateBytes_entry(AbstractInterpreter::MethodKind kind) {
       
   159   if (UseCRC32CIntrinsics) {
       
   160     address entry = __ pc();
       
   161     // Load parameters
       
   162     const Register crc = rax;  // crc
       
   163     const Register buf = rcx;  // source java byte array address
       
   164     const Register len = rdx;  // length
       
   165     const Register end = len;
       
   166 
       
   167     // value              x86_32
       
   168     // interp. arg ptr    ESP + 4
       
   169     // int java.util.zip.CRC32.updateBytes(int crc, byte[] b, int off, int end)
       
   170     //                                         3           2      1        0
       
   171     // int java.util.zip.CRC32.updateByteBuffer(int crc, long address, int off, int end)
       
   172     //                                              4         2,3          1        0
       
   173 
       
   174     // Arguments are reversed on java expression stack
       
   175     __ movl(end, Address(rsp, 4 + 0)); // end
       
   176     __ subl(len, Address(rsp, 4 + 1 * wordSize));  // end - offset == length
       
   177     // Calculate address of start element
       
   178     if (kind == Interpreter::java_util_zip_CRC32C_updateDirectByteBuffer) {
       
   179       __ movptr(buf, Address(rsp, 4 + 2 * wordSize)); // long address
       
   180       __ addptr(buf, Address(rsp, 4 + 1 * wordSize)); // + offset
       
   181       __ movl(crc, Address(rsp, 4 + 4 * wordSize)); // Initial CRC
       
   182     } else {
       
   183       __ movptr(buf, Address(rsp, 4 + 2 * wordSize)); // byte[] array
       
   184       __ addptr(buf, arrayOopDesc::base_offset_in_bytes(T_BYTE)); // + header size
       
   185       __ addptr(buf, Address(rsp, 4 + 1 * wordSize)); // + offset
       
   186       __ movl(crc, Address(rsp, 4 + 3 * wordSize)); // Initial CRC
       
   187     }
       
   188     __ super_call_VM_leaf(CAST_FROM_FN_PTR(address, StubRoutines::updateBytesCRC32C()), crc, buf, len);
       
   189     // result in rax
       
   190     // _areturn
       
   191     __ pop(rdi);                // get return address
       
   192     __ mov(rsp, rsi);           // set sp to sender sp
       
   193     __ jmp(rdi);
       
   194 
       
   195     return entry;
       
   196   }
       
   197   return NULL;
       
   198 }
       
   199 
       
   200 /**
       
   201  * Method entry for static native method:
       
   202  *    java.lang.Float.intBitsToFloat(int bits)
       
   203  */
       
   204 address InterpreterGenerator::generate_Float_intBitsToFloat_entry() {
       
   205   if (UseSSE >= 1) {
       
   206     address entry = __ pc();
       
   207 
       
   208     // rsi: the sender's SP
       
   209 
       
   210     // Skip safepoint check (compiler intrinsic versions of this method
       
   211     // do not perform safepoint checks either).
       
   212 
       
   213     // Load 'bits' into xmm0 (interpreter returns results in xmm0)
       
   214     __ movflt(xmm0, Address(rsp, wordSize));
       
   215 
       
   216     // Return
       
   217     __ pop(rdi); // get return address
       
   218     __ mov(rsp, rsi); // set rsp to the sender's SP
       
   219     __ jmp(rdi);
       
   220     return entry;
       
   221   }
       
   222 
       
   223   return NULL;
       
   224 }
       
   225 
       
   226 /**
       
   227  * Method entry for static native method:
       
   228  *    java.lang.Float.floatToRawIntBits(float value)
       
   229  */
       
   230 address InterpreterGenerator::generate_Float_floatToRawIntBits_entry() {
       
   231   if (UseSSE >= 1) {
       
   232     address entry = __ pc();
       
   233 
       
   234     // rsi: the sender's SP
       
   235 
       
   236     // Skip safepoint check (compiler intrinsic versions of this method
       
   237     // do not perform safepoint checks either).
       
   238 
       
   239     // Load the parameter (a floating-point value) into rax.
       
   240     __ movl(rax, Address(rsp, wordSize));
       
   241 
       
   242     // Return
       
   243     __ pop(rdi); // get return address
       
   244     __ mov(rsp, rsi); // set rsp to the sender's SP
       
   245     __ jmp(rdi);
       
   246     return entry;
       
   247   }
       
   248 
       
   249   return NULL;
       
   250 }
       
   251 
       
   252 
       
   253 /**
       
   254  * Method entry for static native method:
       
   255  *    java.lang.Double.longBitsToDouble(long bits)
       
   256  */
       
   257 address InterpreterGenerator::generate_Double_longBitsToDouble_entry() {
       
   258    if (UseSSE >= 2) {
       
   259      address entry = __ pc();
       
   260 
       
   261      // rsi: the sender's SP
       
   262 
       
   263      // Skip safepoint check (compiler intrinsic versions of this method
       
   264      // do not perform safepoint checks either).
       
   265 
       
   266      // Load 'bits' into xmm0 (interpreter returns results in xmm0)
       
   267      __ movdbl(xmm0, Address(rsp, wordSize));
       
   268 
       
   269      // Return
       
   270      __ pop(rdi); // get return address
       
   271      __ mov(rsp, rsi); // set rsp to the sender's SP
       
   272      __ jmp(rdi);
       
   273      return entry;
       
   274    }
       
   275 
       
   276    return NULL;
       
   277 }
       
   278 
       
   279 /**
       
   280  * Method entry for static native method:
       
   281  *    java.lang.Double.doubleToRawLongBits(double value)
       
   282  */
       
   283 address InterpreterGenerator::generate_Double_doubleToRawLongBits_entry() {
       
   284   if (UseSSE >= 2) {
       
   285     address entry = __ pc();
       
   286 
       
   287     // rsi: the sender's SP
       
   288 
       
   289     // Skip safepoint check (compiler intrinsic versions of this method
       
   290     // do not perform safepoint checks either).
       
   291 
       
   292     // Load the parameter (a floating-point value) into rax.
       
   293     __ movl(rdx, Address(rsp, 2*wordSize));
       
   294     __ movl(rax, Address(rsp, wordSize));
       
   295 
       
   296     // Return
       
   297     __ pop(rdi); // get return address
       
   298     __ mov(rsp, rsi); // set rsp to the sender's SP
       
   299     __ jmp(rdi);
       
   300     return entry;
       
   301   }
       
   302 
       
   303   return NULL;
       
   304 }
       
   305 #endif // CC_INTERP