src/cpu/x86/vm/templateInterpreter_x86_64.cpp

Print this page


   1 /*
   2  * Copyright (c) 2003, 2011, 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  *


 505 #ifdef ASSERT
 506   {
 507     Label L;
 508     __ movl(rax, access_flags);
 509     __ testl(rax, JVM_ACC_SYNCHRONIZED);
 510     __ jcc(Assembler::notZero, L);
 511     __ stop("method doesn't need synchronization");
 512     __ bind(L);
 513   }
 514 #endif // ASSERT
 515 
 516   // get synchronization object
 517   {
 518     const int mirror_offset = in_bytes(Klass::java_mirror_offset());
 519     Label done;
 520     __ movl(rax, access_flags);
 521     __ testl(rax, JVM_ACC_STATIC);
 522     // get receiver (assume this is frequent case)
 523     __ movptr(rax, Address(r14, Interpreter::local_offset_in_bytes(0)));
 524     __ jcc(Assembler::zero, done);
 525     __ movptr(rax, Address(rbx, methodOopDesc::constants_offset()));

 526     __ movptr(rax, Address(rax,
 527                            constantPoolOopDesc::pool_holder_offset_in_bytes()));
 528     __ movptr(rax, Address(rax, mirror_offset));
 529 
 530 #ifdef ASSERT
 531     {
 532       Label L;
 533       __ testptr(rax, rax);
 534       __ jcc(Assembler::notZero, L);
 535       __ stop("synchronization object is NULL");
 536       __ bind(L);
 537     }
 538 #endif // ASSERT
 539 
 540     __ bind(done);
 541   }
 542 
 543   // add space for monitor & lock
 544   __ subptr(rsp, entry_size); // add space for a monitor entry
 545   __ movptr(monitor_block_top, rsp);  // set new monitor block top


 562   // initialize fixed part of activation frame
 563   __ push(rax);        // save return address
 564   __ enter();          // save old & set new rbp
 565   __ push(r13);        // set sender sp
 566   __ push((int)NULL_WORD); // leave last_sp as null
 567   __ movptr(r13, Address(rbx, methodOopDesc::const_offset()));      // get constMethodOop
 568   __ lea(r13, Address(r13, constMethodOopDesc::codes_offset())); // get codebase
 569   __ push(rbx);        // save methodOop
 570   if (ProfileInterpreter) {
 571     Label method_data_continue;
 572     __ movptr(rdx, Address(rbx, in_bytes(methodOopDesc::method_data_offset())));
 573     __ testptr(rdx, rdx);
 574     __ jcc(Assembler::zero, method_data_continue);
 575     __ addptr(rdx, in_bytes(methodDataOopDesc::data_offset()));
 576     __ bind(method_data_continue);
 577     __ push(rdx);      // set the mdp (method data pointer)
 578   } else {
 579     __ push(0);
 580   }
 581 
 582   __ movptr(rdx, Address(rbx, methodOopDesc::constants_offset()));

 583   __ movptr(rdx, Address(rdx, constantPoolOopDesc::cache_offset_in_bytes()));
 584   __ push(rdx); // set constant pool cache
 585   __ push(r14); // set locals pointer
 586   if (native_call) {
 587     __ push(0); // no bcp
 588   } else {
 589     __ push(r13); // set bcp
 590   }
 591   __ push(0); // reserve word for pointer to expression stack bottom
 592   __ movptr(Address(rsp, 0), rsp); // set expression stack bottom
 593 }
 594 
 595 // End of helpers
 596 
 597 // Various method entries
 598 //------------------------------------------------------------------------------------------------------------------------
 599 //
 600 //
 601 
 602 // Call an accessor method (assuming it is resolved, otherwise drop


 612   // do fastpath for resolved accessor methods
 613   if (UseFastAccessorMethods) {
 614     // Code: _aload_0, _(i|a)getfield, _(i|a)return or any rewrites
 615     //       thereof; parameter size = 1
 616     // Note: We can only use this code if the getfield has been resolved
 617     //       and if we don't have a null-pointer exception => check for
 618     //       these conditions first and use slow path if necessary.
 619     Label slow_path;
 620     // If we need a safepoint check, generate full interpreter entry.
 621     __ cmp32(ExternalAddress(SafepointSynchronize::address_of_state()),
 622              SafepointSynchronize::_not_synchronized);
 623 
 624     __ jcc(Assembler::notEqual, slow_path);
 625     // rbx: method
 626     __ movptr(rax, Address(rsp, wordSize));
 627 
 628     // check if local 0 != NULL and read field
 629     __ testptr(rax, rax);
 630     __ jcc(Assembler::zero, slow_path);
 631 
 632     __ movptr(rdi, Address(rbx, methodOopDesc::constants_offset()));
 633     // read first instruction word and extract bytecode @ 1 and index @ 2
 634     __ movptr(rdx, Address(rbx, methodOopDesc::const_offset()));

 635     __ movl(rdx, Address(rdx, constMethodOopDesc::codes_offset()));
 636     // Shift codes right to get the index on the right.
 637     // The bytecode fetched looks like <index><0xb4><0x2a>
 638     __ shrl(rdx, 2 * BitsPerByte);
 639     __ shll(rdx, exact_log2(in_words(ConstantPoolCacheEntry::size())));
 640     __ movptr(rdi, Address(rdi, constantPoolOopDesc::cache_offset_in_bytes()));
 641 
 642     // rax: local 0
 643     // rbx: method
 644     // rdx: constant pool cache index
 645     // rdi: constant pool cache
 646 
 647     // check if getfield has been resolved and read constant pool cache entry
 648     // check the validity of the cache entry by testing whether _indices field
 649     // contains Bytecode::_getfield in b1 byte.
 650     assert(in_words(ConstantPoolCacheEntry::size()) == 4,
 651            "adjust shift below");
 652     __ movl(rcx,
 653             Address(rdi,
 654                     rdx,


1003   // each time here.  The slow-path generator can do a GC on return,
1004   // so we must reload it after the call.
1005   __ call(t);
1006   __ get_method(method);        // slow path can do a GC, reload RBX
1007 
1008 
1009   // result handler is in rax
1010   // set result handler
1011   __ movptr(Address(rbp,
1012                     (frame::interpreter_frame_result_handler_offset) * wordSize),
1013             rax);
1014 
1015   // pass mirror handle if static call
1016   {
1017     Label L;
1018     const int mirror_offset = in_bytes(Klass::java_mirror_offset());
1019     __ movl(t, Address(method, methodOopDesc::access_flags_offset()));
1020     __ testl(t, JVM_ACC_STATIC);
1021     __ jcc(Assembler::zero, L);
1022     // get mirror
1023     __ movptr(t, Address(method, methodOopDesc::constants_offset()));

1024     __ movptr(t, Address(t, constantPoolOopDesc::pool_holder_offset_in_bytes()));
1025     __ movptr(t, Address(t, mirror_offset));
1026     // copy mirror into activation frame
1027     __ movptr(Address(rbp, frame::interpreter_frame_oop_temp_offset * wordSize),
1028             t);
1029     // pass handle to mirror
1030     __ lea(c_rarg1,
1031            Address(rbp, frame::interpreter_frame_oop_temp_offset * wordSize));
1032     __ bind(L);
1033   }
1034 
1035   // get native function entry point
1036   {
1037     Label L;
1038     __ movptr(rax, Address(method, methodOopDesc::native_function_offset()));
1039     ExternalAddress unsatisfied(SharedRuntime::native_method_throw_unsatisfied_link_error_entry());
1040     __ movptr(rscratch2, unsatisfied.addr());
1041     __ cmpptr(rax, rscratch2);
1042     __ jcc(Assembler::notEqual, L);
1043     __ call_VM(noreg,


   1 /*
   2  * Copyright (c) 2003, 2012, 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  *


 505 #ifdef ASSERT
 506   {
 507     Label L;
 508     __ movl(rax, access_flags);
 509     __ testl(rax, JVM_ACC_SYNCHRONIZED);
 510     __ jcc(Assembler::notZero, L);
 511     __ stop("method doesn't need synchronization");
 512     __ bind(L);
 513   }
 514 #endif // ASSERT
 515 
 516   // get synchronization object
 517   {
 518     const int mirror_offset = in_bytes(Klass::java_mirror_offset());
 519     Label done;
 520     __ movl(rax, access_flags);
 521     __ testl(rax, JVM_ACC_STATIC);
 522     // get receiver (assume this is frequent case)
 523     __ movptr(rax, Address(r14, Interpreter::local_offset_in_bytes(0)));
 524     __ jcc(Assembler::zero, done);
 525     __ movptr(rax, Address(rbx, methodOopDesc::const_offset()));
 526     __ movptr(rax, Address(rax, constMethodOopDesc::constants_offset()));
 527     __ movptr(rax, Address(rax,
 528                            constantPoolOopDesc::pool_holder_offset_in_bytes()));
 529     __ movptr(rax, Address(rax, mirror_offset));
 530 
 531 #ifdef ASSERT
 532     {
 533       Label L;
 534       __ testptr(rax, rax);
 535       __ jcc(Assembler::notZero, L);
 536       __ stop("synchronization object is NULL");
 537       __ bind(L);
 538     }
 539 #endif // ASSERT
 540 
 541     __ bind(done);
 542   }
 543 
 544   // add space for monitor & lock
 545   __ subptr(rsp, entry_size); // add space for a monitor entry
 546   __ movptr(monitor_block_top, rsp);  // set new monitor block top


 563   // initialize fixed part of activation frame
 564   __ push(rax);        // save return address
 565   __ enter();          // save old & set new rbp
 566   __ push(r13);        // set sender sp
 567   __ push((int)NULL_WORD); // leave last_sp as null
 568   __ movptr(r13, Address(rbx, methodOopDesc::const_offset()));      // get constMethodOop
 569   __ lea(r13, Address(r13, constMethodOopDesc::codes_offset())); // get codebase
 570   __ push(rbx);        // save methodOop
 571   if (ProfileInterpreter) {
 572     Label method_data_continue;
 573     __ movptr(rdx, Address(rbx, in_bytes(methodOopDesc::method_data_offset())));
 574     __ testptr(rdx, rdx);
 575     __ jcc(Assembler::zero, method_data_continue);
 576     __ addptr(rdx, in_bytes(methodDataOopDesc::data_offset()));
 577     __ bind(method_data_continue);
 578     __ push(rdx);      // set the mdp (method data pointer)
 579   } else {
 580     __ push(0);
 581   }
 582 
 583   __ movptr(rdx, Address(rbx, methodOopDesc::const_offset()));
 584   __ movptr(rdx, Address(rdx, constMethodOopDesc::constants_offset()));
 585   __ movptr(rdx, Address(rdx, constantPoolOopDesc::cache_offset_in_bytes()));
 586   __ push(rdx); // set constant pool cache
 587   __ push(r14); // set locals pointer
 588   if (native_call) {
 589     __ push(0); // no bcp
 590   } else {
 591     __ push(r13); // set bcp
 592   }
 593   __ push(0); // reserve word for pointer to expression stack bottom
 594   __ movptr(Address(rsp, 0), rsp); // set expression stack bottom
 595 }
 596 
 597 // End of helpers
 598 
 599 // Various method entries
 600 //------------------------------------------------------------------------------------------------------------------------
 601 //
 602 //
 603 
 604 // Call an accessor method (assuming it is resolved, otherwise drop


 614   // do fastpath for resolved accessor methods
 615   if (UseFastAccessorMethods) {
 616     // Code: _aload_0, _(i|a)getfield, _(i|a)return or any rewrites
 617     //       thereof; parameter size = 1
 618     // Note: We can only use this code if the getfield has been resolved
 619     //       and if we don't have a null-pointer exception => check for
 620     //       these conditions first and use slow path if necessary.
 621     Label slow_path;
 622     // If we need a safepoint check, generate full interpreter entry.
 623     __ cmp32(ExternalAddress(SafepointSynchronize::address_of_state()),
 624              SafepointSynchronize::_not_synchronized);
 625 
 626     __ jcc(Assembler::notEqual, slow_path);
 627     // rbx: method
 628     __ movptr(rax, Address(rsp, wordSize));
 629 
 630     // check if local 0 != NULL and read field
 631     __ testptr(rax, rax);
 632     __ jcc(Assembler::zero, slow_path);
 633 

 634     // read first instruction word and extract bytecode @ 1 and index @ 2
 635     __ movptr(rdx, Address(rbx, methodOopDesc::const_offset()));
 636     __ movptr(rdi, Address(rdx, constMethodOopDesc::constants_offset()));
 637     __ movl(rdx, Address(rdx, constMethodOopDesc::codes_offset()));
 638     // Shift codes right to get the index on the right.
 639     // The bytecode fetched looks like <index><0xb4><0x2a>
 640     __ shrl(rdx, 2 * BitsPerByte);
 641     __ shll(rdx, exact_log2(in_words(ConstantPoolCacheEntry::size())));
 642     __ movptr(rdi, Address(rdi, constantPoolOopDesc::cache_offset_in_bytes()));
 643 
 644     // rax: local 0
 645     // rbx: method
 646     // rdx: constant pool cache index
 647     // rdi: constant pool cache
 648 
 649     // check if getfield has been resolved and read constant pool cache entry
 650     // check the validity of the cache entry by testing whether _indices field
 651     // contains Bytecode::_getfield in b1 byte.
 652     assert(in_words(ConstantPoolCacheEntry::size()) == 4,
 653            "adjust shift below");
 654     __ movl(rcx,
 655             Address(rdi,
 656                     rdx,


1005   // each time here.  The slow-path generator can do a GC on return,
1006   // so we must reload it after the call.
1007   __ call(t);
1008   __ get_method(method);        // slow path can do a GC, reload RBX
1009 
1010 
1011   // result handler is in rax
1012   // set result handler
1013   __ movptr(Address(rbp,
1014                     (frame::interpreter_frame_result_handler_offset) * wordSize),
1015             rax);
1016 
1017   // pass mirror handle if static call
1018   {
1019     Label L;
1020     const int mirror_offset = in_bytes(Klass::java_mirror_offset());
1021     __ movl(t, Address(method, methodOopDesc::access_flags_offset()));
1022     __ testl(t, JVM_ACC_STATIC);
1023     __ jcc(Assembler::zero, L);
1024     // get mirror
1025     __ movptr(t, Address(method, methodOopDesc::const_offset()));
1026     __ movptr(t, Address(t, constMethodOopDesc::constants_offset()));
1027     __ movptr(t, Address(t, constantPoolOopDesc::pool_holder_offset_in_bytes()));
1028     __ movptr(t, Address(t, mirror_offset));
1029     // copy mirror into activation frame
1030     __ movptr(Address(rbp, frame::interpreter_frame_oop_temp_offset * wordSize),
1031             t);
1032     // pass handle to mirror
1033     __ lea(c_rarg1,
1034            Address(rbp, frame::interpreter_frame_oop_temp_offset * wordSize));
1035     __ bind(L);
1036   }
1037 
1038   // get native function entry point
1039   {
1040     Label L;
1041     __ movptr(rax, Address(method, methodOopDesc::native_function_offset()));
1042     ExternalAddress unsatisfied(SharedRuntime::native_method_throw_unsatisfied_link_error_entry());
1043     __ movptr(rscratch2, unsatisfied.addr());
1044     __ cmpptr(rax, rscratch2);
1045     __ jcc(Assembler::notEqual, L);
1046     __ call_VM(noreg,