objectMonitor.hpp revision 1472:c18cbe5936b8
1/* 2 * Copyright (c) 1998, 2007, Oracle and/or its affiliates. All rights reserved. 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 * 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 7 * published by the Free Software Foundation. 8 * 9 * This code is distributed in the hope that it will be useful, but WITHOUT 10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 11 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 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// WARNING: 26// This is a very sensitive and fragile class. DO NOT make any 27// change unless you are fully aware of the underlying semantics. 28 29// This class can not inherit from any other class, because I have 30// to let the displaced header be the very first word. Otherwise I 31// have to let markOop include this file, which would export the 32// monitor data structure to everywhere. 33// 34// The ObjectMonitor class is used to implement JavaMonitors which have 35// transformed from the lightweight structure of the thread stack to a 36// heavy weight lock due to contention 37 38// It is also used as RawMonitor by the JVMTI 39 40 41class ObjectWaiter; 42 43class ObjectMonitor { 44 public: 45 enum { 46 OM_OK, // no error 47 OM_SYSTEM_ERROR, // operating system error 48 OM_ILLEGAL_MONITOR_STATE, // IllegalMonitorStateException 49 OM_INTERRUPTED, // Thread.interrupt() 50 OM_TIMED_OUT // Object.wait() timed out 51 }; 52 53 public: 54 // TODO-FIXME: the "offset" routines should return a type of off_t instead of int ... 55 // ByteSize would also be an appropriate type. 56 static int header_offset_in_bytes() { return offset_of(ObjectMonitor, _header); } 57 static int object_offset_in_bytes() { return offset_of(ObjectMonitor, _object); } 58 static int owner_offset_in_bytes() { return offset_of(ObjectMonitor, _owner); } 59 static int count_offset_in_bytes() { return offset_of(ObjectMonitor, _count); } 60 static int recursions_offset_in_bytes() { return offset_of(ObjectMonitor, _recursions); } 61 static int cxq_offset_in_bytes() { return offset_of(ObjectMonitor, _cxq) ; } 62 static int succ_offset_in_bytes() { return offset_of(ObjectMonitor, _succ) ; } 63 static int EntryList_offset_in_bytes() { return offset_of(ObjectMonitor, _EntryList); } 64 static int FreeNext_offset_in_bytes() { return offset_of(ObjectMonitor, FreeNext); } 65 static int WaitSet_offset_in_bytes() { return offset_of(ObjectMonitor, _WaitSet) ; } 66 static int Responsible_offset_in_bytes() { return offset_of(ObjectMonitor, _Responsible);} 67 static int Spinner_offset_in_bytes() { return offset_of(ObjectMonitor, _Spinner); } 68 69 public: 70 // Eventaully we'll make provisions for multiple callbacks, but 71 // now one will suffice. 72 static int (*SpinCallbackFunction)(intptr_t, int) ; 73 static intptr_t SpinCallbackArgument ; 74 75 76 public: 77 ObjectMonitor(); 78 ~ObjectMonitor(); 79 80 markOop header() const; 81 void set_header(markOop hdr); 82 83 intptr_t is_busy() const; 84 intptr_t is_entered(Thread* current) const; 85 86 void* owner() const; 87 void set_owner(void* owner); 88 89 intptr_t waiters() const; 90 91 intptr_t count() const; 92 void set_count(intptr_t count); 93 intptr_t contentions() const ; 94 95 // JVM/DI GetMonitorInfo() needs this 96 Thread * thread_of_waiter (ObjectWaiter *) ; 97 ObjectWaiter * first_waiter () ; 98 ObjectWaiter * next_waiter(ObjectWaiter* o); 99 100 intptr_t recursions() const { return _recursions; } 101 102 void* object() const; 103 void* object_addr(); 104 void set_object(void* obj); 105 106 bool check(TRAPS); // true if the thread owns the monitor. 107 void check_slow(TRAPS); 108 void clear(); 109#ifndef PRODUCT 110 void verify(); 111 void print(); 112#endif 113 114 bool try_enter (TRAPS) ; 115 void enter(TRAPS); 116 void exit(TRAPS); 117 void wait(jlong millis, bool interruptable, TRAPS); 118 void notify(TRAPS); 119 void notifyAll(TRAPS); 120 121// Use the following at your own risk 122 intptr_t complete_exit(TRAPS); 123 void reenter(intptr_t recursions, TRAPS); 124 125 int raw_enter(TRAPS); 126 int raw_exit(TRAPS); 127 int raw_wait(jlong millis, bool interruptable, TRAPS); 128 int raw_notify(TRAPS); 129 int raw_notifyAll(TRAPS); 130 131 private: 132 // JVMTI support -- remove ASAP 133 int SimpleEnter (Thread * Self) ; 134 int SimpleExit (Thread * Self) ; 135 int SimpleWait (Thread * Self, jlong millis) ; 136 int SimpleNotify (Thread * Self, bool All) ; 137 138 private: 139 void Recycle () ; 140 void AddWaiter (ObjectWaiter * waiter) ; 141 142 ObjectWaiter * DequeueWaiter () ; 143 void DequeueSpecificWaiter (ObjectWaiter * waiter) ; 144 void EnterI (TRAPS) ; 145 void ReenterI (Thread * Self, ObjectWaiter * SelfNode) ; 146 void UnlinkAfterAcquire (Thread * Self, ObjectWaiter * SelfNode) ; 147 int TryLock (Thread * Self) ; 148 int NotRunnable (Thread * Self, Thread * Owner) ; 149 int TrySpin_Fixed (Thread * Self) ; 150 int TrySpin_VaryFrequency (Thread * Self) ; 151 int TrySpin_VaryDuration (Thread * Self) ; 152 void ctAsserts () ; 153 void ExitEpilog (Thread * Self, ObjectWaiter * Wakee) ; 154 bool ExitSuspendEquivalent (JavaThread * Self) ; 155 156 private: 157 friend class ObjectSynchronizer; 158 friend class ObjectWaiter; 159 friend class VMStructs; 160 161 // WARNING: this must be the very first word of ObjectMonitor 162 // This means this class can't use any virtual member functions. 163 // TODO-FIXME: assert that offsetof(_header) is 0 or get rid of the 164 // implicit 0 offset in emitted code. 165 166 volatile markOop _header; // displaced object header word - mark 167 void* volatile _object; // backward object pointer - strong root 168 169 double SharingPad [1] ; // temp to reduce false sharing 170 171 // All the following fields must be machine word aligned 172 // The VM assumes write ordering wrt these fields, which can be 173 // read from other threads. 174 175 void * volatile _owner; // pointer to owning thread OR BasicLock 176 volatile intptr_t _recursions; // recursion count, 0 for first entry 177 int OwnerIsThread ; // _owner is (Thread *) vs SP/BasicLock 178 ObjectWaiter * volatile _cxq ; // LL of recently-arrived threads blocked on entry. 179 // The list is actually composed of WaitNodes, acting 180 // as proxies for Threads. 181 ObjectWaiter * volatile _EntryList ; // Threads blocked on entry or reentry. 182 Thread * volatile _succ ; // Heir presumptive thread - used for futile wakeup throttling 183 Thread * volatile _Responsible ; 184 int _PromptDrain ; // rqst to drain cxq into EntryList ASAP 185 186 volatile int _Spinner ; // for exit->spinner handoff optimization 187 volatile int _SpinFreq ; // Spin 1-out-of-N attempts: success rate 188 volatile int _SpinClock ; 189 volatile int _SpinDuration ; 190 volatile intptr_t _SpinState ; // MCS/CLH list of spinners 191 192 // TODO-FIXME: _count, _waiters and _recursions should be of 193 // type int, or int32_t but not intptr_t. There's no reason 194 // to use 64-bit fields for these variables on a 64-bit JVM. 195 196 volatile intptr_t _count; // reference count to prevent reclaimation/deflation 197 // at stop-the-world time. See deflate_idle_monitors(). 198 // _count is approximately |_WaitSet| + |_EntryList| 199 volatile intptr_t _waiters; // number of waiting threads 200 ObjectWaiter * volatile _WaitSet; // LL of threads wait()ing on the monitor 201 volatile int _WaitSetLock; // protects Wait Queue - simple spinlock 202 203 public: 204 int _QMix ; // Mixed prepend queue discipline 205 ObjectMonitor * FreeNext ; // Free list linkage 206 intptr_t StatA, StatsB ; 207 208}; 209