Fri, 12 Feb 2010 15:27:36 -0800
Merge
duke@435 | 1 | /* |
xdono@631 | 2 | * Copyright 1999-2008 Sun Microsystems, Inc. All Rights Reserved. |
duke@435 | 3 | * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. |
duke@435 | 4 | * |
duke@435 | 5 | * This code is free software; you can redistribute it and/or modify it |
duke@435 | 6 | * under the terms of the GNU General Public License version 2 only, as |
duke@435 | 7 | * published by the Free Software Foundation. |
duke@435 | 8 | * |
duke@435 | 9 | * This code is distributed in the hope that it will be useful, but WITHOUT |
duke@435 | 10 | * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or |
duke@435 | 11 | * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License |
duke@435 | 12 | * version 2 for more details (a copy is included in the LICENSE file that |
duke@435 | 13 | * accompanied this code). |
duke@435 | 14 | * |
duke@435 | 15 | * You should have received a copy of the GNU General Public License version |
duke@435 | 16 | * 2 along with this work; if not, write to the Free Software Foundation, |
duke@435 | 17 | * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. |
duke@435 | 18 | * |
duke@435 | 19 | * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara, |
duke@435 | 20 | * CA 95054 USA or visit www.sun.com if you need additional information or |
duke@435 | 21 | * have any questions. |
duke@435 | 22 | * |
duke@435 | 23 | */ |
duke@435 | 24 | |
duke@435 | 25 | #include "incls/_precompiled.incl" |
duke@435 | 26 | #include "incls/_locknode.cpp.incl" |
duke@435 | 27 | |
duke@435 | 28 | //============================================================================= |
duke@435 | 29 | const RegMask &BoxLockNode::in_RegMask(uint i) const { |
duke@435 | 30 | return _inmask; |
duke@435 | 31 | } |
duke@435 | 32 | |
duke@435 | 33 | const RegMask &BoxLockNode::out_RegMask() const { |
duke@435 | 34 | return *Matcher::idealreg2regmask[Op_RegP]; |
duke@435 | 35 | } |
duke@435 | 36 | |
duke@435 | 37 | uint BoxLockNode::size_of() const { return sizeof(*this); } |
duke@435 | 38 | |
kvn@501 | 39 | BoxLockNode::BoxLockNode( int slot ) : Node( Compile::current()->root() ), |
kvn@501 | 40 | _slot(slot), _is_eliminated(false) { |
duke@435 | 41 | init_class_id(Class_BoxLock); |
duke@435 | 42 | init_flags(Flag_rematerialize); |
duke@435 | 43 | OptoReg::Name reg = OptoReg::stack2reg(_slot); |
duke@435 | 44 | _inmask.Insert(reg); |
duke@435 | 45 | } |
duke@435 | 46 | |
kvn@895 | 47 | //-----------------------------hash-------------------------------------------- |
kvn@895 | 48 | uint BoxLockNode::hash() const { |
kvn@895 | 49 | return Node::hash() + _slot + (_is_eliminated ? Compile::current()->fixed_slots() : 0); |
kvn@895 | 50 | } |
kvn@895 | 51 | |
duke@435 | 52 | //------------------------------cmp-------------------------------------------- |
duke@435 | 53 | uint BoxLockNode::cmp( const Node &n ) const { |
duke@435 | 54 | const BoxLockNode &bn = (const BoxLockNode &)n; |
kvn@895 | 55 | return bn._slot == _slot && bn._is_eliminated == _is_eliminated; |
duke@435 | 56 | } |
duke@435 | 57 | |
duke@435 | 58 | OptoReg::Name BoxLockNode::stack_slot(Node* box_node) { |
duke@435 | 59 | // Chase down the BoxNode |
duke@435 | 60 | while (!box_node->is_BoxLock()) { |
duke@435 | 61 | // if (box_node->is_SpillCopy()) { |
duke@435 | 62 | // Node *m = box_node->in(1); |
duke@435 | 63 | // if (m->is_Mach() && m->as_Mach()->ideal_Opcode() == Op_StoreP) { |
duke@435 | 64 | // box_node = m->in(m->as_Mach()->operand_index(2)); |
duke@435 | 65 | // continue; |
duke@435 | 66 | // } |
duke@435 | 67 | // } |
duke@435 | 68 | assert(box_node->is_SpillCopy() || box_node->is_Phi(), "Bad spill of Lock."); |
duke@435 | 69 | box_node = box_node->in(1); |
duke@435 | 70 | } |
duke@435 | 71 | return box_node->in_RegMask(0).find_first_elem(); |
duke@435 | 72 | } |
duke@435 | 73 | |
duke@435 | 74 | //============================================================================= |
duke@435 | 75 | //-----------------------------hash-------------------------------------------- |
duke@435 | 76 | uint FastLockNode::hash() const { return NO_HASH; } |
duke@435 | 77 | |
duke@435 | 78 | //------------------------------cmp-------------------------------------------- |
duke@435 | 79 | uint FastLockNode::cmp( const Node &n ) const { |
duke@435 | 80 | return (&n == this); // Always fail except on self |
duke@435 | 81 | } |
duke@435 | 82 | |
duke@435 | 83 | //============================================================================= |
duke@435 | 84 | //-----------------------------hash-------------------------------------------- |
duke@435 | 85 | uint FastUnlockNode::hash() const { return NO_HASH; } |
duke@435 | 86 | |
duke@435 | 87 | //------------------------------cmp-------------------------------------------- |
duke@435 | 88 | uint FastUnlockNode::cmp( const Node &n ) const { |
duke@435 | 89 | return (&n == this); // Always fail except on self |
duke@435 | 90 | } |
duke@435 | 91 | |
duke@435 | 92 | // |
duke@435 | 93 | // Create a counter which counts the number of times this lock is acquired |
duke@435 | 94 | // |
duke@435 | 95 | void FastLockNode::create_lock_counter(JVMState* state) { |
duke@435 | 96 | BiasedLockingNamedCounter* blnc = (BiasedLockingNamedCounter*) |
duke@435 | 97 | OptoRuntime::new_named_counter(state, NamedCounter::BiasedLockingCounter); |
duke@435 | 98 | _counters = blnc->counters(); |
duke@435 | 99 | } |
duke@435 | 100 | |
duke@435 | 101 | //============================================================================= |
duke@435 | 102 | //------------------------------do_monitor_enter------------------------------- |
duke@435 | 103 | void Parse::do_monitor_enter() { |
duke@435 | 104 | kill_dead_locals(); |
duke@435 | 105 | |
duke@435 | 106 | // Null check; get casted pointer. |
duke@435 | 107 | Node *obj = do_null_check(peek(), T_OBJECT); |
duke@435 | 108 | // Check for locking null object |
duke@435 | 109 | if (stopped()) return; |
duke@435 | 110 | |
duke@435 | 111 | // the monitor object is not part of debug info expression stack |
duke@435 | 112 | pop(); |
duke@435 | 113 | |
duke@435 | 114 | // Insert a FastLockNode which takes as arguments the current thread pointer, |
duke@435 | 115 | // the obj pointer & the address of the stack slot pair used for the lock. |
duke@435 | 116 | shared_lock(obj); |
duke@435 | 117 | } |
duke@435 | 118 | |
duke@435 | 119 | //------------------------------do_monitor_exit-------------------------------- |
duke@435 | 120 | void Parse::do_monitor_exit() { |
duke@435 | 121 | kill_dead_locals(); |
duke@435 | 122 | |
duke@435 | 123 | pop(); // Pop oop to unlock |
twisti@1040 | 124 | // Because monitors are guaranteed paired (else we bail out), we know |
duke@435 | 125 | // the matching Lock for this Unlock. Hence we know there is no need |
duke@435 | 126 | // for a null check on Unlock. |
duke@435 | 127 | shared_unlock(map()->peek_monitor_box(), map()->peek_monitor_obj()); |
duke@435 | 128 | } |