--- old/src/cpu/sparc/vm/sparc.ad 2011-07-22 11:55:08.650124080 +0200 +++ new/src/cpu/sparc/vm/sparc.ad 2011-07-22 11:55:08.426773347 +0200 @@ -6606,8 +6606,7 @@ %} instruct membar_acquire_lock() %{ - match(MemBarAcquire); - predicate(Matcher::prior_fast_lock(n)); + match(MemBarAcquireLock); ins_cost(0); size(0); @@ -6627,8 +6626,7 @@ %} instruct membar_release_lock() %{ - match(MemBarRelease); - predicate(Matcher::post_fast_unlock(n)); + match(MemBarReleaseLock); ins_cost(0); size(0); --- old/src/cpu/x86/vm/x86_32.ad 2011-07-22 11:55:10.572377938 +0200 +++ new/src/cpu/x86/vm/x86_32.ad 2011-07-22 11:55:10.334618251 +0200 @@ -7806,8 +7806,7 @@ %} instruct membar_acquire_lock() %{ - match(MemBarAcquire); - predicate(Matcher::prior_fast_lock(n)); + match(MemBarAcquireLock); ins_cost(0); size(0); @@ -7827,8 +7826,7 @@ %} instruct membar_release_lock() %{ - match(MemBarRelease); - predicate(Matcher::post_fast_unlock(n)); + match(MemBarReleaseLock); ins_cost(0); size(0); --- old/src/cpu/x86/vm/x86_64.ad 2011-07-22 11:55:12.446184011 +0200 +++ new/src/cpu/x86/vm/x86_64.ad 2011-07-22 11:55:12.231393843 +0200 @@ -7376,8 +7376,7 @@ instruct membar_acquire_lock() %{ - match(MemBarAcquire); - predicate(Matcher::prior_fast_lock(n)); + match(MemBarAcquireLock); ins_cost(0); size(0); @@ -7399,8 +7398,7 @@ instruct membar_release_lock() %{ - match(MemBarRelease); - predicate(Matcher::post_fast_unlock(n)); + match(MemBarReleaseLock); ins_cost(0); size(0); --- old/src/share/vm/opto/classes.hpp 2011-07-22 11:55:14.262756282 +0200 +++ new/src/share/vm/opto/classes.hpp 2011-07-22 11:55:14.100896776 +0200 @@ -161,8 +161,10 @@ macro(MachProj) macro(MaxI) macro(MemBarAcquire) +macro(MemBarAcquireLock) macro(MemBarCPUOrder) macro(MemBarRelease) +macro(MemBarReleaseLock) macro(MemBarVolatile) macro(MergeMem) macro(MinI) --- old/src/share/vm/opto/graphKit.cpp 2011-07-22 11:55:15.919628772 +0200 +++ new/src/share/vm/opto/graphKit.cpp 2011-07-22 11:55:15.731470259 +0200 @@ -2856,7 +2856,7 @@ // lock has no side-effects, sets few values set_predefined_output_for_runtime_call(lock, mem, TypeRawPtr::BOTTOM); - insert_mem_bar(Op_MemBarAcquire); + insert_mem_bar(Op_MemBarAcquireLock); // Add this to the worklist so that the lock can be eliminated record_for_igvn(lock); @@ -2889,7 +2889,7 @@ } // Memory barrier to avoid floating things down past the locked region - insert_mem_bar(Op_MemBarRelease); + insert_mem_bar(Op_MemBarReleaseLock); const TypeFunc *tf = OptoRuntime::complete_monitor_exit_Type(); UnlockNode *unlock = new (C, tf->domain()->cnt()) UnlockNode(C, tf); --- old/src/share/vm/opto/macro.cpp 2011-07-22 11:55:17.438774715 +0200 +++ new/src/share/vm/opto/macro.cpp 2011-07-22 11:55:17.260663709 +0200 @@ -1816,9 +1816,9 @@ // The input to a Lock is merged memory, so extract its RawMem input // (unless the MergeMem has been optimized away.) if (alock->is_Lock()) { - // Seach for MemBarAcquire node and delete it also. + // Seach for MemBarAcquireLock node and delete it also. MemBarNode* membar = fallthroughproj->unique_ctrl_out()->as_MemBar(); - assert(membar != NULL && membar->Opcode() == Op_MemBarAcquire, ""); + assert(membar != NULL && membar->Opcode() == Op_MemBarAcquireLock, ""); Node* ctrlproj = membar->proj_out(TypeFunc::Control); Node* memproj = membar->proj_out(TypeFunc::Memory); _igvn.replace_node(ctrlproj, fallthroughproj); @@ -1833,11 +1833,11 @@ } } - // Seach for MemBarRelease node and delete it also. + // Seach for MemBarReleaseLock node and delete it also. if (alock->is_Unlock() && ctrl != NULL && ctrl->is_Proj() && ctrl->in(0)->is_MemBar()) { MemBarNode* membar = ctrl->in(0)->as_MemBar(); - assert(membar->Opcode() == Op_MemBarRelease && + assert(membar->Opcode() == Op_MemBarReleaseLock && mem->is_Proj() && membar == mem->in(0), ""); _igvn.replace_node(fallthroughproj, ctrl); _igvn.replace_node(memproj_fallthrough, mem); --- old/src/share/vm/opto/matcher.cpp 2011-07-22 11:55:18.864395671 +0200 +++ new/src/share/vm/opto/matcher.cpp 2011-07-22 11:55:18.690771794 +0200 @@ -2230,57 +2230,6 @@ } } - -// Used by the DFA in dfa_sparc.cpp. Check for a prior FastLock -// acting as an Acquire and thus we don't need an Acquire here. We -// retain the Node to act as a compiler ordering barrier. -bool Matcher::prior_fast_lock( const Node *acq ) { - Node *r = acq->in(0); - if( !r->is_Region() || r->req() <= 1 ) return false; - Node *proj = r->in(1); - if( !proj->is_Proj() ) return false; - Node *call = proj->in(0); - if( !call->is_Call() || call->as_Call()->entry_point() != OptoRuntime::complete_monitor_locking_Java() ) - return false; - - return true; -} - -// Used by the DFA in dfa_sparc.cpp. Check for a following FastUnLock -// acting as a Release and thus we don't need a Release here. We -// retain the Node to act as a compiler ordering barrier. -bool Matcher::post_fast_unlock( const Node *rel ) { - Compile *C = Compile::current(); - assert( rel->Opcode() == Op_MemBarRelease, "" ); - const MemBarReleaseNode *mem = (const MemBarReleaseNode*)rel; - DUIterator_Fast imax, i = mem->fast_outs(imax); - Node *ctrl = NULL; - while( true ) { - ctrl = mem->fast_out(i); // Throw out-of-bounds if proj not found - assert( ctrl->is_Proj(), "only projections here" ); - ProjNode *proj = (ProjNode*)ctrl; - if( proj->_con == TypeFunc::Control && - !C->node_arena()->contains(ctrl) ) // Unmatched old-space only - break; - i++; - } - Node *iff = NULL; - for( DUIterator_Fast jmax, j = ctrl->fast_outs(jmax); j < jmax; j++ ) { - Node *x = ctrl->fast_out(j); - if( x->is_If() && x->req() > 1 && - !C->node_arena()->contains(x) ) { // Unmatched old-space only - iff = x; - break; - } - } - if( !iff ) return false; - Node *bol = iff->in(1); - // The iff might be some random subclass of If or bol might be Con-Top - if (!bol->is_Bool()) return false; - assert( bol->req() > 1, "" ); - return (bol->in(1)->Opcode() == Op_FastUnlock); -} - // Used by the DFA in dfa_xxx.cpp. Check for a following barrier or // atomic instruction acting as a store_load barrier without any // intervening volatile load, and thus we don't need a barrier here. --- old/src/share/vm/opto/matcher.hpp 2011-07-22 11:55:20.247298127 +0200 +++ new/src/share/vm/opto/matcher.hpp 2011-07-22 11:55:20.081634069 +0200 @@ -441,16 +441,6 @@ else { fatal("SoftMatchFailure is not allowed except in product"); } } - // Used by the DFA in dfa_sparc.cpp. Check for a prior FastLock - // acting as an Acquire and thus we don't need an Acquire here. We - // retain the Node to act as a compiler ordering barrier. - static bool prior_fast_lock( const Node *acq ); - - // Used by the DFA in dfa_sparc.cpp. Check for a following - // FastUnLock acting as a Release and thus we don't need a Release - // here. We retain the Node to act as a compiler ordering barrier. - static bool post_fast_unlock( const Node *rel ); - // Check for a following volatile memory barrier without an // intervening load and thus we don't need a barrier here. We // retain the Node to act as a compiler ordering barrier. --- old/src/share/vm/opto/memnode.cpp 2011-07-22 11:55:21.585454326 +0200 +++ new/src/share/vm/opto/memnode.cpp 2011-07-22 11:55:21.390242987 +0200 @@ -925,8 +925,9 @@ // a synchronized region. while (current->is_Proj()) { int opc = current->in(0)->Opcode(); - if ((final && opc == Op_MemBarAcquire) || - opc == Op_MemBarRelease || opc == Op_MemBarCPUOrder) { + if ((final && (opc == Op_MemBarAcquire || opc == Op_MemBarAcquireLock)) || + opc == Op_MemBarRelease || opc == Op_MemBarCPUOrder || + opc == Op_MemBarReleaseLock) { Node* mem = current->in(0)->in(TypeFunc::Memory); if (mem->is_MergeMem()) { MergeMemNode* merge = mem->as_MergeMem(); @@ -2666,6 +2667,8 @@ switch (opcode) { case Op_MemBarAcquire: return new(C, len) MemBarAcquireNode(C, atp, pn); case Op_MemBarRelease: return new(C, len) MemBarReleaseNode(C, atp, pn); + case Op_MemBarAcquireLock: return new(C, len) MemBarAcquireLockNode(C, atp, pn); + case Op_MemBarReleaseLock: return new(C, len) MemBarReleaseLockNode(C, atp, pn); case Op_MemBarVolatile: return new(C, len) MemBarVolatileNode(C, atp, pn); case Op_MemBarCPUOrder: return new(C, len) MemBarCPUOrderNode(C, atp, pn); case Op_Initialize: return new(C, len) InitializeNode(C, atp, pn); --- old/src/share/vm/opto/memnode.hpp 2011-07-22 11:55:23.110461480 +0200 +++ new/src/share/vm/opto/memnode.hpp 2011-07-22 11:55:22.944403491 +0200 @@ -879,7 +879,7 @@ // "Acquire" - no following ref can move before (but earlier refs can // follow, like an early Load stalled in cache). Requires multi-cpu -// visibility. Inserted after a volatile load or FastLock. +// visibility. Inserted after a volatile load. class MemBarAcquireNode: public MemBarNode { public: MemBarAcquireNode(Compile* C, int alias_idx, Node* precedent) @@ -889,13 +889,33 @@ // "Release" - no earlier ref can move after (but later refs can move // up, like a speculative pipelined cache-hitting Load). Requires -// multi-cpu visibility. Inserted before a volatile store or FastUnLock. +// multi-cpu visibility. Inserted before a volatile store. class MemBarReleaseNode: public MemBarNode { public: MemBarReleaseNode(Compile* C, int alias_idx, Node* precedent) : MemBarNode(C, alias_idx, precedent) {} virtual int Opcode() const; }; + +// "Acquire" - no following ref can move before (but earlier refs can +// follow, like an early Load stalled in cache). Requires multi-cpu +// visibility. Inserted after a FastLock. +class MemBarAcquireLockNode: public MemBarNode { +public: + MemBarAcquireLockNode(Compile* C, int alias_idx, Node* precedent) + : MemBarNode(C, alias_idx, precedent) {} + virtual int Opcode() const; +}; + +// "Release" - no earlier ref can move after (but later refs can move +// up, like a speculative pipelined cache-hitting Load). Requires +// multi-cpu visibility. Inserted before a FastUnLock. +class MemBarReleaseLockNode: public MemBarNode { +public: + MemBarReleaseLockNode(Compile* C, int alias_idx, Node* precedent) + : MemBarNode(C, alias_idx, precedent) {} + virtual int Opcode() const; +}; // Ordering between a volatile store and a following volatile load. // Requires multi-CPU visibility?