< prev index next >

src/hotspot/cpu/x86/nativeInst_x86.hpp

Print this page
rev 47415 : Add Thread Local handshakes and thread local polling


  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 #ifndef CPU_X86_VM_NATIVEINST_X86_HPP
  26 #define CPU_X86_VM_NATIVEINST_X86_HPP
  27 
  28 #include "asm/assembler.hpp"
  29 #include "memory/allocation.hpp"
  30 #include "runtime/icache.hpp"
  31 #include "runtime/os.hpp"

  32 
  33 // We have interfaces for the following instructions:
  34 // - NativeInstruction
  35 // - - NativeCall
  36 // - - NativeMovConstReg
  37 // - - NativeMovConstRegPatching
  38 // - - NativeMovRegMem
  39 // - - NativeMovRegMemPatching
  40 // - - NativeJump
  41 // - - NativeFarJump
  42 // - - NativeIllegalOpCode
  43 // - - NativeGeneralJump
  44 // - - NativeReturn
  45 // - - NativeReturnX (return with argument)
  46 // - - NativePushConst
  47 // - - NativeTstRegMem
  48 
  49 // The base class for different kinds of native instruction abstractions.
  50 // Provides the primitive operations to manipulate code relative to this.
  51 


 661   };
 662 };
 663 
 664 // return instruction that does pop values of the stack
 665 class NativeReturnX: public NativeInstruction {
 666  public:
 667   enum Intel_specific_constants {
 668     instruction_code            = 0xC2,
 669     instruction_size            =    2,
 670     instruction_offset          =    0,
 671     next_instruction_offset     =    2
 672   };
 673 };
 674 
 675 // Simple test vs memory
 676 class NativeTstRegMem: public NativeInstruction {
 677  public:
 678   enum Intel_specific_constants {
 679     instruction_rex_prefix_mask = 0xF0,
 680     instruction_rex_prefix      = Assembler::REX,

 681     instruction_code_memXregl   = 0x85,
 682     modrm_mask                  = 0x38, // select reg from the ModRM byte
 683     modrm_reg                   = 0x00  // rax
 684   };
 685 };
 686 
 687 inline bool NativeInstruction::is_illegal()      { return (short)int_at(0) == (short)NativeIllegalInstruction::instruction_code; }
 688 inline bool NativeInstruction::is_call()         { return ubyte_at(0) == NativeCall::instruction_code; }
 689 inline bool NativeInstruction::is_call_reg()     { return ubyte_at(0) == NativeCallReg::instruction_code ||
 690                                                           (ubyte_at(1) == NativeCallReg::instruction_code &&
 691                                                            (ubyte_at(0) == Assembler::REX || ubyte_at(0) == Assembler::REX_B)); }
 692 inline bool NativeInstruction::is_return()       { return ubyte_at(0) == NativeReturn::instruction_code ||
 693                                                           ubyte_at(0) == NativeReturnX::instruction_code; }
 694 inline bool NativeInstruction::is_jump()         { return ubyte_at(0) == NativeJump::instruction_code ||
 695                                                           ubyte_at(0) == 0xEB; /* short jump */ }
 696 inline bool NativeInstruction::is_jump_reg()     {
 697   int pos = 0;
 698   if (ubyte_at(0) == Assembler::REX_B) pos = 1;
 699   return ubyte_at(pos) == 0xFF && (ubyte_at(pos + 1) & 0xF0) == 0xE0;
 700 }
 701 inline bool NativeInstruction::is_far_jump()     { return is_mov_literal64(); }
 702 inline bool NativeInstruction::is_cond_jump()    { return (int_at(0) & 0xF0FF) == 0x800F /* long jump */ ||
 703                                                           (ubyte_at(0) & 0xF0) == 0x70;  /* short jump */ }
 704 inline bool NativeInstruction::is_safepoint_poll() {
 705 #ifdef AMD64










 706   // Try decoding a near safepoint first:
 707   if (ubyte_at(0) == NativeTstRegMem::instruction_code_memXregl &&
 708       ubyte_at(1) == 0x05) { // 00 rax 101
 709     address fault = addr_at(6) + int_at(2);
 710     NOT_JVMCI(assert(!Assembler::is_polling_page_far(), "unexpected poll encoding");)
 711     return os::is_poll_address(fault);
 712   }
 713   // Now try decoding a far safepoint:
 714   // two cases, depending on the choice of the base register in the address.
 715   if (((ubyte_at(0) & NativeTstRegMem::instruction_rex_prefix_mask) == NativeTstRegMem::instruction_rex_prefix &&
 716        ubyte_at(1) == NativeTstRegMem::instruction_code_memXregl &&
 717        (ubyte_at(2) & NativeTstRegMem::modrm_mask) == NativeTstRegMem::modrm_reg) ||
 718       (ubyte_at(0) == NativeTstRegMem::instruction_code_memXregl &&
 719        (ubyte_at(1) & NativeTstRegMem::modrm_mask) == NativeTstRegMem::modrm_reg)) {
 720     NOT_JVMCI(assert(Assembler::is_polling_page_far(), "unexpected poll encoding");)
 721     return true;
 722   }
 723   return false;
 724 #else
 725   return ( ubyte_at(0) == NativeMovRegMem::instruction_code_mem2reg ||


  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 #ifndef CPU_X86_VM_NATIVEINST_X86_HPP
  26 #define CPU_X86_VM_NATIVEINST_X86_HPP
  27 
  28 #include "asm/assembler.hpp"
  29 #include "memory/allocation.hpp"
  30 #include "runtime/icache.hpp"
  31 #include "runtime/os.hpp"
  32 #include "runtime/safepointMechanism.hpp"
  33 
  34 // We have interfaces for the following instructions:
  35 // - NativeInstruction
  36 // - - NativeCall
  37 // - - NativeMovConstReg
  38 // - - NativeMovConstRegPatching
  39 // - - NativeMovRegMem
  40 // - - NativeMovRegMemPatching
  41 // - - NativeJump
  42 // - - NativeFarJump
  43 // - - NativeIllegalOpCode
  44 // - - NativeGeneralJump
  45 // - - NativeReturn
  46 // - - NativeReturnX (return with argument)
  47 // - - NativePushConst
  48 // - - NativeTstRegMem
  49 
  50 // The base class for different kinds of native instruction abstractions.
  51 // Provides the primitive operations to manipulate code relative to this.
  52 


 662   };
 663 };
 664 
 665 // return instruction that does pop values of the stack
 666 class NativeReturnX: public NativeInstruction {
 667  public:
 668   enum Intel_specific_constants {
 669     instruction_code            = 0xC2,
 670     instruction_size            =    2,
 671     instruction_offset          =    0,
 672     next_instruction_offset     =    2
 673   };
 674 };
 675 
 676 // Simple test vs memory
 677 class NativeTstRegMem: public NativeInstruction {
 678  public:
 679   enum Intel_specific_constants {
 680     instruction_rex_prefix_mask = 0xF0,
 681     instruction_rex_prefix      = Assembler::REX,
 682     instruction_rex_b_prefix    = Assembler::REX_B,
 683     instruction_code_memXregl   = 0x85,
 684     modrm_mask                  = 0x38, // select reg from the ModRM byte
 685     modrm_reg                   = 0x00  // rax
 686   };
 687 };
 688 
 689 inline bool NativeInstruction::is_illegal()      { return (short)int_at(0) == (short)NativeIllegalInstruction::instruction_code; }
 690 inline bool NativeInstruction::is_call()         { return ubyte_at(0) == NativeCall::instruction_code; }
 691 inline bool NativeInstruction::is_call_reg()     { return ubyte_at(0) == NativeCallReg::instruction_code ||
 692                                                           (ubyte_at(1) == NativeCallReg::instruction_code &&
 693                                                            (ubyte_at(0) == Assembler::REX || ubyte_at(0) == Assembler::REX_B)); }
 694 inline bool NativeInstruction::is_return()       { return ubyte_at(0) == NativeReturn::instruction_code ||
 695                                                           ubyte_at(0) == NativeReturnX::instruction_code; }
 696 inline bool NativeInstruction::is_jump()         { return ubyte_at(0) == NativeJump::instruction_code ||
 697                                                           ubyte_at(0) == 0xEB; /* short jump */ }
 698 inline bool NativeInstruction::is_jump_reg()     {
 699   int pos = 0;
 700   if (ubyte_at(0) == Assembler::REX_B) pos = 1;
 701   return ubyte_at(pos) == 0xFF && (ubyte_at(pos + 1) & 0xF0) == 0xE0;
 702 }
 703 inline bool NativeInstruction::is_far_jump()     { return is_mov_literal64(); }
 704 inline bool NativeInstruction::is_cond_jump()    { return (int_at(0) & 0xF0FF) == 0x800F /* long jump */ ||
 705                                                           (ubyte_at(0) & 0xF0) == 0x70;  /* short jump */ }
 706 inline bool NativeInstruction::is_safepoint_poll() {
 707 #ifdef AMD64
 708   if (SafepointMechanism::uses_thread_local_poll()) {
 709     // We know that the poll must have a REX_B prefix since we enforce its source to be
 710     // a rex-register and the destination to be rax.
 711     const bool has_rex_prefix = ubyte_at(0) == NativeTstRegMem::instruction_rex_b_prefix;
 712     const bool is_test_opcode = ubyte_at(1) == NativeTstRegMem::instruction_code_memXregl;
 713     const bool is_rax_target = (ubyte_at(2) & NativeTstRegMem::modrm_mask) == NativeTstRegMem::modrm_reg;
 714     if (has_rex_prefix && is_test_opcode && is_rax_target) {
 715       return true;
 716     }
 717   }
 718   // Try decoding a near safepoint first:
 719   if (ubyte_at(0) == NativeTstRegMem::instruction_code_memXregl &&
 720       ubyte_at(1) == 0x05) { // 00 rax 101
 721     address fault = addr_at(6) + int_at(2);
 722     NOT_JVMCI(assert(!Assembler::is_polling_page_far(), "unexpected poll encoding");)
 723     return os::is_poll_address(fault);
 724   }
 725   // Now try decoding a far safepoint:
 726   // two cases, depending on the choice of the base register in the address.
 727   if (((ubyte_at(0) & NativeTstRegMem::instruction_rex_prefix_mask) == NativeTstRegMem::instruction_rex_prefix &&
 728        ubyte_at(1) == NativeTstRegMem::instruction_code_memXregl &&
 729        (ubyte_at(2) & NativeTstRegMem::modrm_mask) == NativeTstRegMem::modrm_reg) ||
 730       (ubyte_at(0) == NativeTstRegMem::instruction_code_memXregl &&
 731        (ubyte_at(1) & NativeTstRegMem::modrm_mask) == NativeTstRegMem::modrm_reg)) {
 732     NOT_JVMCI(assert(Assembler::is_polling_page_far(), "unexpected poll encoding");)
 733     return true;
 734   }
 735   return false;
 736 #else
 737   return ( ubyte_at(0) == NativeMovRegMem::instruction_code_mem2reg ||
< prev index next >