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