src/cpu/x86/vm/interpreterRT_x86_64.cpp

Thu, 07 Oct 2010 08:06:06 -0700

author
coleenp
date
Thu, 07 Oct 2010 08:06:06 -0700
changeset 2222
b6aedd1acdc0
parent 1907
c18cbe5936b8
child 2314
f95d63e2154a
permissions
-rw-r--r--

6983240: guarantee((Solaris::min_stack_allowed >= (StackYellowPages+StackRedPages...) wrong
Summary: min_stack_allowed is a compile time constant and Stack*Pages are settable
Reviewed-by: dholmes, kvn

     1 /*
     2  * Copyright (c) 2003, 2010, 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  */
    25 #include "incls/_precompiled.incl"
    26 #include "incls/_interpreterRT_x86_64.cpp.incl"
    28 #define __ _masm->
    30 // Implementation of SignatureHandlerGenerator
    32 Register InterpreterRuntime::SignatureHandlerGenerator::from() { return r14; }
    33 Register InterpreterRuntime::SignatureHandlerGenerator::to()   { return rsp; }
    34 Register InterpreterRuntime::SignatureHandlerGenerator::temp() { return rscratch1; }
    36 void InterpreterRuntime::SignatureHandlerGenerator::pass_int() {
    37   const Address src(from(), Interpreter::local_offset_in_bytes(offset()));
    39 #ifdef _WIN64
    40   switch (_num_args) {
    41   case 0:
    42     __ movl(c_rarg1, src);
    43     _num_args++;
    44     break;
    45   case 1:
    46     __ movl(c_rarg2, src);
    47     _num_args++;
    48     break;
    49   case 2:
    50     __ movl(c_rarg3, src);
    51     _num_args++;
    52     break;
    53   default:
    54     __ movl(rax, src);
    55     __ movl(Address(to(), _stack_offset), rax);
    56     _stack_offset += wordSize;
    57     break;
    58   }
    59 #else
    60   switch (_num_int_args) {
    61   case 0:
    62     __ movl(c_rarg1, src);
    63     _num_int_args++;
    64     break;
    65   case 1:
    66     __ movl(c_rarg2, src);
    67     _num_int_args++;
    68     break;
    69   case 2:
    70     __ movl(c_rarg3, src);
    71     _num_int_args++;
    72     break;
    73   case 3:
    74     __ movl(c_rarg4, src);
    75     _num_int_args++;
    76     break;
    77   case 4:
    78     __ movl(c_rarg5, src);
    79     _num_int_args++;
    80     break;
    81   default:
    82     __ movl(rax, src);
    83     __ movl(Address(to(), _stack_offset), rax);
    84     _stack_offset += wordSize;
    85     break;
    86   }
    87 #endif
    88 }
    90 void InterpreterRuntime::SignatureHandlerGenerator::pass_long() {
    91   const Address src(from(), Interpreter::local_offset_in_bytes(offset() + 1));
    93 #ifdef _WIN64
    94   switch (_num_args) {
    95   case 0:
    96     __ movptr(c_rarg1, src);
    97     _num_args++;
    98     break;
    99   case 1:
   100     __ movptr(c_rarg2, src);
   101     _num_args++;
   102     break;
   103   case 2:
   104     __ movptr(c_rarg3, src);
   105     _num_args++;
   106     break;
   107   case 3:
   108   default:
   109     __ movptr(rax, src);
   110     __ movptr(Address(to(), _stack_offset), rax);
   111     _stack_offset += wordSize;
   112     break;
   113   }
   114 #else
   115   switch (_num_int_args) {
   116   case 0:
   117     __ movptr(c_rarg1, src);
   118     _num_int_args++;
   119     break;
   120   case 1:
   121     __ movptr(c_rarg2, src);
   122     _num_int_args++;
   123     break;
   124   case 2:
   125     __ movptr(c_rarg3, src);
   126     _num_int_args++;
   127     break;
   128   case 3:
   129     __ movptr(c_rarg4, src);
   130     _num_int_args++;
   131     break;
   132   case 4:
   133     __ movptr(c_rarg5, src);
   134     _num_int_args++;
   135     break;
   136   default:
   137     __ movptr(rax, src);
   138     __ movptr(Address(to(), _stack_offset), rax);
   139     _stack_offset += wordSize;
   140     break;
   141   }
   142 #endif
   143 }
   145 void InterpreterRuntime::SignatureHandlerGenerator::pass_float() {
   146   const Address src(from(), Interpreter::local_offset_in_bytes(offset()));
   148 #ifdef _WIN64
   149   if (_num_args < Argument::n_float_register_parameters_c-1) {
   150     __ movflt(as_XMMRegister(++_num_args), src);
   151   } else {
   152     __ movl(rax, src);
   153     __ movl(Address(to(), _stack_offset), rax);
   154     _stack_offset += wordSize;
   155   }
   156 #else
   157   if (_num_fp_args < Argument::n_float_register_parameters_c) {
   158     __ movflt(as_XMMRegister(_num_fp_args++), src);
   159   } else {
   160     __ movl(rax, src);
   161     __ movl(Address(to(), _stack_offset), rax);
   162     _stack_offset += wordSize;
   163   }
   164 #endif
   165 }
   167 void InterpreterRuntime::SignatureHandlerGenerator::pass_double() {
   168   const Address src(from(), Interpreter::local_offset_in_bytes(offset() + 1));
   170 #ifdef _WIN64
   171   if (_num_args < Argument::n_float_register_parameters_c-1) {
   172     __ movdbl(as_XMMRegister(++_num_args), src);
   173   } else {
   174     __ movptr(rax, src);
   175     __ movptr(Address(to(), _stack_offset), rax);
   176     _stack_offset += wordSize;
   177   }
   178 #else
   179   if (_num_fp_args < Argument::n_float_register_parameters_c) {
   180     __ movdbl(as_XMMRegister(_num_fp_args++), src);
   181   } else {
   182     __ movptr(rax, src);
   183     __ movptr(Address(to(), _stack_offset), rax);
   184     _stack_offset += wordSize;
   185   }
   186 #endif
   187 }
   189 void InterpreterRuntime::SignatureHandlerGenerator::pass_object() {
   190   const Address src(from(), Interpreter::local_offset_in_bytes(offset()));
   192 #ifdef _WIN64
   193   switch (_num_args) {
   194   case 0:
   195     assert(offset() == 0, "argument register 1 can only be (non-null) receiver");
   196     __ lea(c_rarg1, src);
   197     _num_args++;
   198     break;
   199   case 1:
   200     __ lea(rax, src);
   201     __ xorl(c_rarg2, c_rarg2);
   202     __ cmpptr(src, 0);
   203     __ cmov(Assembler::notEqual, c_rarg2, rax);
   204     _num_args++;
   205     break;
   206   case 2:
   207     __ lea(rax, src);
   208     __ xorl(c_rarg3, c_rarg3);
   209     __ cmpptr(src, 0);
   210     __ cmov(Assembler::notEqual, c_rarg3, rax);
   211     _num_args++;
   212     break;
   213   default:
   214     __ lea(rax, src);
   215     __ xorl(temp(), temp());
   216     __ cmpptr(src, 0);
   217     __ cmov(Assembler::notEqual, temp(), rax);
   218     __ movptr(Address(to(), _stack_offset), temp());
   219     _stack_offset += wordSize;
   220     break;
   221   }
   222 #else
   223   switch (_num_int_args) {
   224   case 0:
   225     assert(offset() == 0, "argument register 1 can only be (non-null) receiver");
   226     __ lea(c_rarg1, src);
   227     _num_int_args++;
   228     break;
   229   case 1:
   230     __ lea(rax, src);
   231     __ xorl(c_rarg2, c_rarg2);
   232     __ cmpptr(src, 0);
   233     __ cmov(Assembler::notEqual, c_rarg2, rax);
   234     _num_int_args++;
   235     break;
   236   case 2:
   237     __ lea(rax, src);
   238     __ xorl(c_rarg3, c_rarg3);
   239     __ cmpptr(src, 0);
   240     __ cmov(Assembler::notEqual, c_rarg3, rax);
   241     _num_int_args++;
   242     break;
   243   case 3:
   244     __ lea(rax, src);
   245     __ xorl(c_rarg4, c_rarg4);
   246     __ cmpptr(src, 0);
   247     __ cmov(Assembler::notEqual, c_rarg4, rax);
   248     _num_int_args++;
   249     break;
   250   case 4:
   251     __ lea(rax, src);
   252     __ xorl(c_rarg5, c_rarg5);
   253     __ cmpptr(src, 0);
   254     __ cmov(Assembler::notEqual, c_rarg5, rax);
   255     _num_int_args++;
   256     break;
   257   default:
   258     __ lea(rax, src);
   259     __ xorl(temp(), temp());
   260     __ cmpptr(src, 0);
   261     __ cmov(Assembler::notEqual, temp(), rax);
   262     __ movptr(Address(to(), _stack_offset), temp());
   263     _stack_offset += wordSize;
   264     break;
   265   }
   266 #endif
   267 }
   269 void InterpreterRuntime::SignatureHandlerGenerator::generate(uint64_t fingerprint) {
   270   // generate code to handle arguments
   271   iterate(fingerprint);
   273   // return result handler
   274   __ lea(rax, ExternalAddress(Interpreter::result_handler(method()->result_type())));
   275   __ ret(0);
   277   __ flush();
   278 }
   281 // Implementation of SignatureHandlerLibrary
   283 void SignatureHandlerLibrary::pd_set_handler(address handler) {}
   286 #ifdef _WIN64
   287 class SlowSignatureHandler
   288   : public NativeSignatureIterator {
   289  private:
   290   address   _from;
   291   intptr_t* _to;
   292   intptr_t* _reg_args;
   293   intptr_t* _fp_identifiers;
   294   unsigned int _num_args;
   296   virtual void pass_int()
   297   {
   298     jint from_obj = *(jint *)(_from+Interpreter::local_offset_in_bytes(0));
   299     _from -= Interpreter::stackElementSize;
   301     if (_num_args < Argument::n_int_register_parameters_c-1) {
   302       *_reg_args++ = from_obj;
   303       _num_args++;
   304     } else {
   305       *_to++ = from_obj;
   306     }
   307   }
   309   virtual void pass_long()
   310   {
   311     intptr_t from_obj = *(intptr_t*)(_from+Interpreter::local_offset_in_bytes(1));
   312     _from -= 2*Interpreter::stackElementSize;
   314     if (_num_args < Argument::n_int_register_parameters_c-1) {
   315       *_reg_args++ = from_obj;
   316       _num_args++;
   317     } else {
   318       *_to++ = from_obj;
   319     }
   320   }
   322   virtual void pass_object()
   323   {
   324     intptr_t *from_addr = (intptr_t*)(_from + Interpreter::local_offset_in_bytes(0));
   325     _from -= Interpreter::stackElementSize;
   326     if (_num_args < Argument::n_int_register_parameters_c-1) {
   327       *_reg_args++ = (*from_addr == 0) ? NULL : (intptr_t) from_addr;
   328       _num_args++;
   329     } else {
   330       *_to++ = (*from_addr == 0) ? NULL : (intptr_t) from_addr;
   331     }
   332   }
   334   virtual void pass_float()
   335   {
   336     jint from_obj = *(jint *)(_from+Interpreter::local_offset_in_bytes(0));
   337     _from -= Interpreter::stackElementSize;
   339     if (_num_args < Argument::n_float_register_parameters_c-1) {
   340       *_reg_args++ = from_obj;
   341       *_fp_identifiers |= (intptr_t)(0x01 << (_num_args*2)); // mark as float
   342       _num_args++;
   343     } else {
   344       *_to++ = from_obj;
   345     }
   346   }
   348   virtual void pass_double()
   349   {
   350     intptr_t from_obj = *(intptr_t*)(_from+Interpreter::local_offset_in_bytes(1));
   351     _from -= 2*Interpreter::stackElementSize;
   353     if (_num_args < Argument::n_float_register_parameters_c-1) {
   354       *_reg_args++ = from_obj;
   355       *_fp_identifiers |= (intptr_t)(0x3 << (_num_args*2)); // mark as double
   356       _num_args++;
   357     } else {
   358       *_to++ = from_obj;
   359     }
   360   }
   362  public:
   363   SlowSignatureHandler(methodHandle method, address from, intptr_t* to)
   364     : NativeSignatureIterator(method)
   365   {
   366     _from = from;
   367     _to   = to;
   369     _reg_args = to - (method->is_static() ? 4 : 5);
   370     _fp_identifiers = to - 2;
   371     _to = _to + 4;  // Windows reserves stack space for register arguments
   372     *(int*) _fp_identifiers = 0;
   373     _num_args = (method->is_static() ? 1 : 0);
   374   }
   375 };
   376 #else
   377 class SlowSignatureHandler
   378   : public NativeSignatureIterator {
   379  private:
   380   address   _from;
   381   intptr_t* _to;
   382   intptr_t* _int_args;
   383   intptr_t* _fp_args;
   384   intptr_t* _fp_identifiers;
   385   unsigned int _num_int_args;
   386   unsigned int _num_fp_args;
   388   virtual void pass_int()
   389   {
   390     jint from_obj = *(jint *)(_from+Interpreter::local_offset_in_bytes(0));
   391     _from -= Interpreter::stackElementSize;
   393     if (_num_int_args < Argument::n_int_register_parameters_c-1) {
   394       *_int_args++ = from_obj;
   395       _num_int_args++;
   396     } else {
   397       *_to++ = from_obj;
   398     }
   399   }
   401   virtual void pass_long()
   402   {
   403     intptr_t from_obj = *(intptr_t*)(_from+Interpreter::local_offset_in_bytes(1));
   404     _from -= 2*Interpreter::stackElementSize;
   406     if (_num_int_args < Argument::n_int_register_parameters_c-1) {
   407       *_int_args++ = from_obj;
   408       _num_int_args++;
   409     } else {
   410       *_to++ = from_obj;
   411     }
   412   }
   414   virtual void pass_object()
   415   {
   416     intptr_t *from_addr = (intptr_t*)(_from + Interpreter::local_offset_in_bytes(0));
   417     _from -= Interpreter::stackElementSize;
   419     if (_num_int_args < Argument::n_int_register_parameters_c-1) {
   420       *_int_args++ = (*from_addr == 0) ? NULL : (intptr_t)from_addr;
   421       _num_int_args++;
   422     } else {
   423       *_to++ = (*from_addr == 0) ? NULL : (intptr_t) from_addr;
   424     }
   425   }
   427   virtual void pass_float()
   428   {
   429     jint from_obj = *(jint*)(_from+Interpreter::local_offset_in_bytes(0));
   430     _from -= Interpreter::stackElementSize;
   432     if (_num_fp_args < Argument::n_float_register_parameters_c) {
   433       *_fp_args++ = from_obj;
   434       _num_fp_args++;
   435     } else {
   436       *_to++ = from_obj;
   437     }
   438   }
   440   virtual void pass_double()
   441   {
   442     intptr_t from_obj = *(intptr_t*)(_from+Interpreter::local_offset_in_bytes(1));
   443     _from -= 2*Interpreter::stackElementSize;
   445     if (_num_fp_args < Argument::n_float_register_parameters_c) {
   446       *_fp_args++ = from_obj;
   447       *_fp_identifiers |= (1 << _num_fp_args); // mark as double
   448       _num_fp_args++;
   449     } else {
   450       *_to++ = from_obj;
   451     }
   452   }
   454  public:
   455   SlowSignatureHandler(methodHandle method, address from, intptr_t* to)
   456     : NativeSignatureIterator(method)
   457   {
   458     _from = from;
   459     _to   = to;
   461     _int_args = to - (method->is_static() ? 14 : 15);
   462     _fp_args =  to - 9;
   463     _fp_identifiers = to - 10;
   464     *(int*) _fp_identifiers = 0;
   465     _num_int_args = (method->is_static() ? 1 : 0);
   466     _num_fp_args = 0;
   467   }
   468 };
   469 #endif
   472 IRT_ENTRY(address,
   473           InterpreterRuntime::slow_signature_handler(JavaThread* thread,
   474                                                      methodOopDesc* method,
   475                                                      intptr_t* from,
   476                                                      intptr_t* to))
   477   methodHandle m(thread, (methodOop)method);
   478   assert(m->is_native(), "sanity check");
   480   // handle arguments
   481   SlowSignatureHandler(m, (address)from, to + 1).iterate(UCONST64(-1));
   483   // return result handler
   484   return Interpreter::result_handler(m->result_type());
   485 IRT_END

mercurial