Mercurial > hg > graal-jvmci-8
comparison src/share/vm/opto/library_call.cpp @ 12169:29aa8936f03c
8023597: Optimize G1 barriers code for unsafe load_store
Summary: Avoid loading old values in G1 pre-barriers for inlined unsafe load_store nodes.
Reviewed-by: kvn, tonyp
Contributed-by: Martin Doerr <martin.doerr@sap.com>
author | kvn |
---|---|
date | Wed, 28 Aug 2013 11:22:43 +0200 |
parents | acedd49a1bce |
children | edb5ab0f3fe5 7944aba7ba41 |
comparison
equal
deleted
inserted
replaced
12168:7181dd13a6c4 | 12169:29aa8936f03c |
---|---|
2754 // Execute transformation here to avoid barrier generation in such case. | 2754 // Execute transformation here to avoid barrier generation in such case. |
2755 if (_gvn.type(newval) == TypePtr::NULL_PTR) | 2755 if (_gvn.type(newval) == TypePtr::NULL_PTR) |
2756 newval = _gvn.makecon(TypePtr::NULL_PTR); | 2756 newval = _gvn.makecon(TypePtr::NULL_PTR); |
2757 | 2757 |
2758 // Reference stores need a store barrier. | 2758 // Reference stores need a store barrier. |
2759 pre_barrier(true /* do_load*/, | 2759 if (kind == LS_xchg) { |
2760 control(), base, adr, alias_idx, newval, value_type->make_oopptr(), | 2760 // If pre-barrier must execute before the oop store, old value will require do_load here. |
2761 NULL /* pre_val*/, | 2761 if (!can_move_pre_barrier()) { |
2762 T_OBJECT); | 2762 pre_barrier(true /* do_load*/, |
2763 control(), base, adr, alias_idx, newval, value_type->make_oopptr(), | |
2764 NULL /* pre_val*/, | |
2765 T_OBJECT); | |
2766 } // Else move pre_barrier to use load_store value, see below. | |
2767 } else if (kind == LS_cmpxchg) { | |
2768 // Same as for newval above: | |
2769 if (_gvn.type(oldval) == TypePtr::NULL_PTR) { | |
2770 oldval = _gvn.makecon(TypePtr::NULL_PTR); | |
2771 } | |
2772 // The only known value which might get overwritten is oldval. | |
2773 pre_barrier(false /* do_load */, | |
2774 control(), NULL, NULL, max_juint, NULL, NULL, | |
2775 oldval /* pre_val */, | |
2776 T_OBJECT); | |
2777 } else { | |
2778 ShouldNotReachHere(); | |
2779 } | |
2780 | |
2763 #ifdef _LP64 | 2781 #ifdef _LP64 |
2764 if (adr->bottom_type()->is_ptr_to_narrowoop()) { | 2782 if (adr->bottom_type()->is_ptr_to_narrowoop()) { |
2765 Node *newval_enc = _gvn.transform(new (C) EncodePNode(newval, newval->bottom_type()->make_narrowoop())); | 2783 Node *newval_enc = _gvn.transform(new (C) EncodePNode(newval, newval->bottom_type()->make_narrowoop())); |
2766 if (kind == LS_xchg) { | 2784 if (kind == LS_xchg) { |
2767 load_store = _gvn.transform(new (C) GetAndSetNNode(control(), mem, adr, | 2785 load_store = _gvn.transform(new (C) GetAndSetNNode(control(), mem, adr, |
2793 // main role is to prevent LoadStore nodes from being optimized away | 2811 // main role is to prevent LoadStore nodes from being optimized away |
2794 // when their results aren't used. | 2812 // when their results aren't used. |
2795 Node* proj = _gvn.transform(new (C) SCMemProjNode(load_store)); | 2813 Node* proj = _gvn.transform(new (C) SCMemProjNode(load_store)); |
2796 set_memory(proj, alias_idx); | 2814 set_memory(proj, alias_idx); |
2797 | 2815 |
2816 if (type == T_OBJECT && kind == LS_xchg) { | |
2817 #ifdef _LP64 | |
2818 if (adr->bottom_type()->is_ptr_to_narrowoop()) { | |
2819 load_store = _gvn.transform(new (C) DecodeNNode(load_store, load_store->get_ptr_type())); | |
2820 } | |
2821 #endif | |
2822 if (can_move_pre_barrier()) { | |
2823 // Don't need to load pre_val. The old value is returned by load_store. | |
2824 // The pre_barrier can execute after the xchg as long as no safepoint | |
2825 // gets inserted between them. | |
2826 pre_barrier(false /* do_load */, | |
2827 control(), NULL, NULL, max_juint, NULL, NULL, | |
2828 load_store /* pre_val */, | |
2829 T_OBJECT); | |
2830 } | |
2831 } | |
2832 | |
2798 // Add the trailing membar surrounding the access | 2833 // Add the trailing membar surrounding the access |
2799 insert_mem_bar(Op_MemBarCPUOrder); | 2834 insert_mem_bar(Op_MemBarCPUOrder); |
2800 insert_mem_bar(Op_MemBarAcquire); | 2835 insert_mem_bar(Op_MemBarAcquire); |
2801 | |
2802 #ifdef _LP64 | |
2803 if (type == T_OBJECT && adr->bottom_type()->is_ptr_to_narrowoop() && kind == LS_xchg) { | |
2804 load_store = _gvn.transform(new (C) DecodeNNode(load_store, load_store->get_ptr_type())); | |
2805 } | |
2806 #endif | |
2807 | 2836 |
2808 assert(type2size[load_store->bottom_type()->basic_type()] == type2size[rtype], "result type should match"); | 2837 assert(type2size[load_store->bottom_type()->basic_type()] == type2size[rtype], "result type should match"); |
2809 set_result(load_store); | 2838 set_result(load_store); |
2810 return true; | 2839 return true; |
2811 } | 2840 } |