Mercurial > hg > truffle
comparison src/cpu/x86/vm/stubGenerator_x86_32.cpp @ 11173:6b0fd0964b87
Merge with http://hg.openjdk.java.net/hsx/hsx25/hotspot/
author | Doug Simon <doug.simon@oracle.com> |
---|---|
date | Wed, 31 Jul 2013 11:00:54 +0200 |
parents | 40b8c383bc31 980532a806a5 |
children | 58fc8e2b7b6d |
comparison
equal
deleted
inserted
replaced
10912:4ea54634f03e | 11173:6b0fd0964b87 |
---|---|
1 /* | 1 /* |
2 * Copyright (c) 1999, 2012, Oracle and/or its affiliates. All rights reserved. | 2 * Copyright (c) 1999, 2013, Oracle and/or its affiliates. All rights reserved. |
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. | 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. |
4 * | 4 * |
5 * This code is free software; you can redistribute it and/or modify it | 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 | 6 * under the terms of the GNU General Public License version 2 only, as |
7 * published by the Free Software Foundation. | 7 * published by the Free Software Foundation. |
81 | 81 |
82 class StubGenerator: public StubCodeGenerator { | 82 class StubGenerator: public StubCodeGenerator { |
83 private: | 83 private: |
84 | 84 |
85 #ifdef PRODUCT | 85 #ifdef PRODUCT |
86 #define inc_counter_np(counter) (0) | 86 #define inc_counter_np(counter) ((void)0) |
87 #else | 87 #else |
88 void inc_counter_np_(int& counter) { | 88 void inc_counter_np_(int& counter) { |
89 __ incrementl(ExternalAddress((address)&counter)); | 89 __ incrementl(ExternalAddress((address)&counter)); |
90 } | 90 } |
91 #define inc_counter_np(counter) \ | 91 #define inc_counter_np(counter) \ |
2711 __ jmp(L_exit); | 2711 __ jmp(L_exit); |
2712 | 2712 |
2713 return start; | 2713 return start; |
2714 } | 2714 } |
2715 | 2715 |
2716 /** | |
2717 * Arguments: | |
2718 * | |
2719 * Inputs: | |
2720 * rsp(4) - int crc | |
2721 * rsp(8) - byte* buf | |
2722 * rsp(12) - int length | |
2723 * | |
2724 * Ouput: | |
2725 * rax - int crc result | |
2726 */ | |
2727 address generate_updateBytesCRC32() { | |
2728 assert(UseCRC32Intrinsics, "need AVX and CLMUL instructions"); | |
2729 | |
2730 __ align(CodeEntryAlignment); | |
2731 StubCodeMark mark(this, "StubRoutines", "updateBytesCRC32"); | |
2732 | |
2733 address start = __ pc(); | |
2734 | |
2735 const Register crc = rdx; // crc | |
2736 const Register buf = rsi; // source java byte array address | |
2737 const Register len = rcx; // length | |
2738 const Register table = rdi; // crc_table address (reuse register) | |
2739 const Register tmp = rbx; | |
2740 assert_different_registers(crc, buf, len, table, tmp, rax); | |
2741 | |
2742 BLOCK_COMMENT("Entry:"); | |
2743 __ enter(); // required for proper stackwalking of RuntimeStub frame | |
2744 __ push(rsi); | |
2745 __ push(rdi); | |
2746 __ push(rbx); | |
2747 | |
2748 Address crc_arg(rbp, 8 + 0); | |
2749 Address buf_arg(rbp, 8 + 4); | |
2750 Address len_arg(rbp, 8 + 8); | |
2751 | |
2752 // Load up: | |
2753 __ movl(crc, crc_arg); | |
2754 __ movptr(buf, buf_arg); | |
2755 __ movl(len, len_arg); | |
2756 | |
2757 __ kernel_crc32(crc, buf, len, table, tmp); | |
2758 | |
2759 __ movl(rax, crc); | |
2760 __ pop(rbx); | |
2761 __ pop(rdi); | |
2762 __ pop(rsi); | |
2763 __ leave(); // required for proper stackwalking of RuntimeStub frame | |
2764 __ ret(0); | |
2765 | |
2766 return start; | |
2767 } | |
2768 | |
2769 // Safefetch stubs. | |
2770 void generate_safefetch(const char* name, int size, address* entry, | |
2771 address* fault_pc, address* continuation_pc) { | |
2772 // safefetch signatures: | |
2773 // int SafeFetch32(int* adr, int errValue); | |
2774 // intptr_t SafeFetchN (intptr_t* adr, intptr_t errValue); | |
2775 | |
2776 StubCodeMark mark(this, "StubRoutines", name); | |
2777 | |
2778 // Entry point, pc or function descriptor. | |
2779 *entry = __ pc(); | |
2780 | |
2781 __ movl(rax, Address(rsp, 0x8)); | |
2782 __ movl(rcx, Address(rsp, 0x4)); | |
2783 // Load *adr into eax, may fault. | |
2784 *fault_pc = __ pc(); | |
2785 switch (size) { | |
2786 case 4: | |
2787 // int32_t | |
2788 __ movl(rax, Address(rcx, 0)); | |
2789 break; | |
2790 case 8: | |
2791 // int64_t | |
2792 Unimplemented(); | |
2793 break; | |
2794 default: | |
2795 ShouldNotReachHere(); | |
2796 } | |
2797 | |
2798 // Return errValue or *adr. | |
2799 *continuation_pc = __ pc(); | |
2800 __ ret(0); | |
2801 } | |
2716 | 2802 |
2717 public: | 2803 public: |
2718 // Information about frame layout at time of blocking runtime call. | 2804 // Information about frame layout at time of blocking runtime call. |
2719 // Note that we only have to preserve callee-saved registers since | 2805 // Note that we only have to preserve callee-saved registers since |
2720 // the compilers are responsible for supplying a continuation point | 2806 // the compilers are responsible for supplying a continuation point |
2885 StubRoutines::_d2l_wrapper = generate_d2i_wrapper(T_LONG, | 2971 StubRoutines::_d2l_wrapper = generate_d2i_wrapper(T_LONG, |
2886 CAST_FROM_FN_PTR(address, SharedRuntime::d2l)); | 2972 CAST_FROM_FN_PTR(address, SharedRuntime::d2l)); |
2887 | 2973 |
2888 // Build this early so it's available for the interpreter | 2974 // Build this early so it's available for the interpreter |
2889 StubRoutines::_throw_StackOverflowError_entry = generate_throw_exception("StackOverflowError throw_exception", CAST_FROM_FN_PTR(address, SharedRuntime::throw_StackOverflowError)); | 2975 StubRoutines::_throw_StackOverflowError_entry = generate_throw_exception("StackOverflowError throw_exception", CAST_FROM_FN_PTR(address, SharedRuntime::throw_StackOverflowError)); |
2976 | |
2977 if (UseCRC32Intrinsics) { | |
2978 // set table address before stub generation which use it | |
2979 StubRoutines::_crc_table_adr = (address)StubRoutines::x86::_crc_table; | |
2980 StubRoutines::_updateBytesCRC32 = generate_updateBytesCRC32(); | |
2981 } | |
2890 } | 2982 } |
2891 | 2983 |
2892 | 2984 |
2893 void generate_all() { | 2985 void generate_all() { |
2894 // Generates all stubs and initializes the entry points | 2986 // Generates all stubs and initializes the entry points |
2918 StubRoutines::_aescrypt_encryptBlock = generate_aescrypt_encryptBlock(); | 3010 StubRoutines::_aescrypt_encryptBlock = generate_aescrypt_encryptBlock(); |
2919 StubRoutines::_aescrypt_decryptBlock = generate_aescrypt_decryptBlock(); | 3011 StubRoutines::_aescrypt_decryptBlock = generate_aescrypt_decryptBlock(); |
2920 StubRoutines::_cipherBlockChaining_encryptAESCrypt = generate_cipherBlockChaining_encryptAESCrypt(); | 3012 StubRoutines::_cipherBlockChaining_encryptAESCrypt = generate_cipherBlockChaining_encryptAESCrypt(); |
2921 StubRoutines::_cipherBlockChaining_decryptAESCrypt = generate_cipherBlockChaining_decryptAESCrypt(); | 3013 StubRoutines::_cipherBlockChaining_decryptAESCrypt = generate_cipherBlockChaining_decryptAESCrypt(); |
2922 } | 3014 } |
3015 | |
3016 // Safefetch stubs. | |
3017 generate_safefetch("SafeFetch32", sizeof(int), &StubRoutines::_safefetch32_entry, | |
3018 &StubRoutines::_safefetch32_fault_pc, | |
3019 &StubRoutines::_safefetch32_continuation_pc); | |
3020 StubRoutines::_safefetchN_entry = StubRoutines::_safefetch32_entry; | |
3021 StubRoutines::_safefetchN_fault_pc = StubRoutines::_safefetch32_fault_pc; | |
3022 StubRoutines::_safefetchN_continuation_pc = StubRoutines::_safefetch32_continuation_pc; | |
2923 } | 3023 } |
2924 | 3024 |
2925 | 3025 |
2926 public: | 3026 public: |
2927 StubGenerator(CodeBuffer* code, bool all) : StubCodeGenerator(code) { | 3027 StubGenerator(CodeBuffer* code, bool all) : StubCodeGenerator(code) { |