| GNU Classpath (0.97.2) | |
| Frames | No Frames |
1: /* 2: * Written by Doug Lea with assistance from members of JCP JSR-166 3: * Expert Group and released to the public domain, as explained at 4: * http://creativecommons.org/licenses/publicdomain 5: */ 6: 7: package java.util.concurrent.locks; 8: import java.util.*; 9: import java.util.concurrent.*; 10: import java.util.concurrent.atomic.*; 11: import sun.misc.Unsafe; 12: 13: /** 14: * A version of {@link AbstractQueuedSynchronizer} in 15: * which synchronization state is maintained as a <tt>long</tt>. 16: * This class has exactly the same structure, properties, and methods 17: * as <tt>AbstractQueuedSynchronizer</tt> with the exception 18: * that all state-related parameters and results are defined 19: * as <tt>long</tt> rather than <tt>int</tt>. This class 20: * may be useful when creating synchronizers such as 21: * multilevel locks and barriers that require 22: * 64 bits of state. 23: * 24: * <p>See {@link AbstractQueuedSynchronizer} for usage 25: * notes and examples. 26: * 27: * @since 1.6 28: * @author Doug Lea 29: */ 30: public abstract class AbstractQueuedLongSynchronizer 31: extends AbstractOwnableSynchronizer 32: implements java.io.Serializable { 33: 34: private static final long serialVersionUID = 7373984972572414692L; 35: 36: /* 37: To keep sources in sync, the remainder of this source file is 38: exactly cloned from AbstractQueuedSynchronizer, replacing class 39: name and changing ints related with sync state to longs. Please 40: keep it that way. 41: */ 42: 43: /** 44: * Creates a new <tt>AbstractQueuedLongSynchronizer</tt> instance 45: * with initial synchronization state of zero. 46: */ 47: protected AbstractQueuedLongSynchronizer() { } 48: 49: /** 50: * Wait queue node class. 51: * 52: * <p>The wait queue is a variant of a "CLH" (Craig, Landin, and 53: * Hagersten) lock queue. CLH locks are normally used for 54: * spinlocks. We instead use them for blocking synchronizers, but 55: * use the same basic tactic of holding some of the control 56: * information about a thread in the predecessor of its node. A 57: * "status" field in each node keeps track of whether a thread 58: * should block. A node is signalled when its predecessor 59: * releases. Each node of the queue otherwise serves as a 60: * specific-notification-style monitor holding a single waiting 61: * thread. The status field does NOT control whether threads are 62: * granted locks etc though. A thread may try to acquire if it is 63: * first in the queue. But being first does not guarantee success; 64: * it only gives the right to contend. So the currently released 65: * contender thread may need to rewait. 66: * 67: * <p>To enqueue into a CLH lock, you atomically splice it in as new 68: * tail. To dequeue, you just set the head field. 69: * <pre> 70: * +------+ prev +-----+ +-----+ 71: * head | | <---- | | <---- | | tail 72: * +------+ +-----+ +-----+ 73: * </pre> 74: * 75: * <p>Insertion into a CLH queue requires only a single atomic 76: * operation on "tail", so there is a simple atomic point of 77: * demarcation from unqueued to queued. Similarly, dequeing 78: * involves only updating the "head". However, it takes a bit 79: * more work for nodes to determine who their successors are, 80: * in part to deal with possible cancellation due to timeouts 81: * and interrupts. 82: * 83: * <p>The "prev" links (not used in original CLH locks), are mainly 84: * needed to handle cancellation. If a node is cancelled, its 85: * successor is (normally) relinked to a non-cancelled 86: * predecessor. For explanation of similar mechanics in the case 87: * of spin locks, see the papers by Scott and Scherer at 88: * http://www.cs.rochester.edu/u/scott/synchronization/ 89: * 90: * <p>We also use "next" links to implement blocking mechanics. 91: * The thread id for each node is kept in its own node, so a 92: * predecessor signals the next node to wake up by traversing 93: * next link to determine which thread it is. Determination of 94: * successor must avoid races with newly queued nodes to set 95: * the "next" fields of their predecessors. This is solved 96: * when necessary by checking backwards from the atomically 97: * updated "tail" when a node's successor appears to be null. 98: * (Or, said differently, the next-links are an optimization 99: * so that we don't usually need a backward scan.) 100: * 101: * <p>Cancellation introduces some conservatism to the basic 102: * algorithms. Since we must poll for cancellation of other 103: * nodes, we can miss noticing whether a cancelled node is 104: * ahead or behind us. This is dealt with by always unparking 105: * successors upon cancellation, allowing them to stabilize on 106: * a new predecessor. 107: * 108: * <p>CLH queues need a dummy header node to get started. But 109: * we don't create them on construction, because it would be wasted 110: * effort if there is never contention. Instead, the node 111: * is constructed and head and tail pointers are set upon first 112: * contention. 113: * 114: * <p>Threads waiting on Conditions use the same nodes, but 115: * use an additional link. Conditions only need to link nodes 116: * in simple (non-concurrent) linked queues because they are 117: * only accessed when exclusively held. Upon await, a node is 118: * inserted into a condition queue. Upon signal, the node is 119: * transferred to the main queue. A special value of status 120: * field is used to mark which queue a node is on. 121: * 122: * <p>Thanks go to Dave Dice, Mark Moir, Victor Luchangco, Bill 123: * Scherer and Michael Scott, along with members of JSR-166 124: * expert group, for helpful ideas, discussions, and critiques 125: * on the design of this class. 126: */ 127: static final class Node { 128: /** waitStatus value to indicate thread has cancelled */ 129: static final int CANCELLED = 1; 130: /** waitStatus value to indicate successor's thread needs unparking */ 131: static final int SIGNAL = -1; 132: /** waitStatus value to indicate thread is waiting on condition */ 133: static final int CONDITION = -2; 134: /** Marker to indicate a node is waiting in shared mode */ 135: static final Node SHARED = new Node(); 136: /** Marker to indicate a node is waiting in exclusive mode */ 137: static final Node EXCLUSIVE = null; 138: 139: /** 140: * Status field, taking on only the values: 141: * SIGNAL: The successor of this node is (or will soon be) 142: * blocked (via park), so the current node must 143: * unpark its successor when it releases or 144: * cancels. To avoid races, acquire methods must 145: * first indicate they need a signal, 146: * then retry the atomic acquire, and then, 147: * on failure, block. 148: * CANCELLED: This node is cancelled due to timeout or interrupt. 149: * Nodes never leave this state. In particular, 150: * a thread with cancelled node never again blocks. 151: * CONDITION: This node is currently on a condition queue. 152: * It will not be used as a sync queue node until 153: * transferred. (Use of this value here 154: * has nothing to do with the other uses 155: * of the field, but simplifies mechanics.) 156: * 0: None of the above 157: * 158: * The values are arranged numerically to simplify use. 159: * Non-negative values mean that a node doesn't need to 160: * signal. So, most code doesn't need to check for particular 161: * values, just for sign. 162: * 163: * The field is initialized to 0 for normal sync nodes, and 164: * CONDITION for condition nodes. It is modified only using 165: * CAS. 166: */ 167: volatile int waitStatus; 168: 169: /** 170: * Link to predecessor node that current node/thread relies on 171: * for checking waitStatus. Assigned during enqueing, and nulled 172: * out (for sake of GC) only upon dequeuing. Also, upon 173: * cancellation of a predecessor, we short-circuit while 174: * finding a non-cancelled one, which will always exist 175: * because the head node is never cancelled: A node becomes 176: * head only as a result of successful acquire. A 177: * cancelled thread never succeeds in acquiring, and a thread only 178: * cancels itself, not any other node. 179: */ 180: volatile Node prev; 181: 182: /** 183: * Link to the successor node that the current node/thread 184: * unparks upon release. Assigned once during enqueuing, and 185: * nulled out (for sake of GC) when no longer needed. Upon 186: * cancellation, we cannot adjust this field, but can notice 187: * status and bypass the node if cancelled. The enq operation 188: * does not assign next field of a predecessor until after 189: * attachment, so seeing a null next field does not 190: * necessarily mean that node is at end of queue. However, if 191: * a next field appears to be null, we can scan prev's from 192: * the tail to double-check. 193: */ 194: volatile Node next; 195: 196: /** 197: * The thread that enqueued this node. Initialized on 198: * construction and nulled out after use. 199: */ 200: volatile Thread thread; 201: 202: /** 203: * Link to next node waiting on condition, or the special 204: * value SHARED. Because condition queues are accessed only 205: * when holding in exclusive mode, we just need a simple 206: * linked queue to hold nodes while they are waiting on 207: * conditions. They are then transferred to the queue to 208: * re-acquire. And because conditions can only be exclusive, 209: * we save a field by using special value to indicate shared 210: * mode. 211: */ 212: Node nextWaiter; 213: 214: /** 215: * Returns true if node is waiting in shared mode 216: */ 217: final boolean isShared() { 218: return nextWaiter == SHARED; 219: } 220: 221: /** 222: * Returns previous node, or throws NullPointerException if 223: * null. Use when predecessor cannot be null. 224: * @return the predecessor of this node 225: */ 226: final Node predecessor() throws NullPointerException { 227: Node p = prev; 228: if (p == null) 229: throw new NullPointerException(); 230: else 231: return p; 232: } 233: 234: Node() { // Used to establish initial head or SHARED marker 235: } 236: 237: Node(Thread thread, Node mode) { // Used by addWaiter 238: this.nextWaiter = mode; 239: this.thread = thread; 240: } 241: 242: Node(Thread thread, int waitStatus) { // Used by Condition 243: this.waitStatus = waitStatus; 244: this.thread = thread; 245: } 246: } 247: 248: /** 249: * Head of the wait queue, lazily initialized. Except for 250: * initialization, it is modified only via method setHead. Note: 251: * If head exists, its waitStatus is guaranteed not to be 252: * CANCELLED. 253: */ 254: private transient volatile Node head; 255: 256: /** 257: * Tail of the wait queue, lazily initialized. Modified only via 258: * method enq to add new wait node. 259: */ 260: private transient volatile Node tail; 261: 262: /** 263: * The synchronization state. 264: */ 265: private volatile long state; 266: 267: /** 268: * Returns the current value of synchronization state. 269: * This operation has memory semantics of a <tt>volatile</tt> read. 270: * @return current state value 271: */ 272: protected final long getState() { 273: return state; 274: } 275: 276: /** 277: * Sets the value of synchronization state. 278: * This operation has memory semantics of a <tt>volatile</tt> write. 279: * @param newState the new state value 280: */ 281: protected final void setState(long newState) { 282: state = newState; 283: } 284: 285: /** 286: * Atomically sets synchronization state to the given updated 287: * value if the current state value equals the expected value. 288: * This operation has memory semantics of a <tt>volatile</tt> read 289: * and write. 290: * 291: * @param expect the expected value 292: * @param update the new value 293: * @return true if successful. False return indicates that the actual 294: * value was not equal to the expected value. 295: */ 296: protected final boolean compareAndSetState(long expect, long update) { 297: // See below for intrinsics setup to support this 298: return unsafe.compareAndSwapLong(this, stateOffset, expect, update); 299: } 300: 301: // Queuing utilities 302: 303: /** 304: * The number of nanoseconds for which it is faster to spin 305: * rather than to use timed park. A rough estimate suffices 306: * to improve responsiveness with very short timeouts. 307: */ 308: static final long spinForTimeoutThreshold = 1000L; 309: 310: /** 311: * Inserts node into queue, initializing if necessary. See picture above. 312: * @param node the node to insert 313: * @return node's predecessor 314: */ 315: private Node enq(final Node node) { 316: for (;;) { 317: Node t = tail; 318: if (t == null) { // Must initialize 319: Node h = new Node(); // Dummy header 320: h.next = node; 321: node.prev = h; 322: if (compareAndSetHead(h)) { 323: tail = node; 324: return h; 325: } 326: } 327: else { 328: node.prev = t; 329: if (compareAndSetTail(t, node)) { 330: t.next = node; 331: return t; 332: } 333: } 334: } 335: } 336: 337: /** 338: * Creates and enqueues node for given thread and mode. 339: * 340: * @param current the thread 341: * @param mode Node.EXCLUSIVE for exclusive, Node.SHARED for shared 342: * @return the new node 343: */ 344: private Node addWaiter(Node mode) { 345: Node node = new Node(Thread.currentThread(), mode); 346: // Try the fast path of enq; backup to full enq on failure 347: Node pred = tail; 348: if (pred != null) { 349: node.prev = pred; 350: if (compareAndSetTail(pred, node)) { 351: pred.next = node; 352: return node; 353: } 354: } 355: enq(node); 356: return node; 357: } 358: 359: /** 360: * Sets head of queue to be node, thus dequeuing. Called only by 361: * acquire methods. Also nulls out unused fields for sake of GC 362: * and to suppress unnecessary signals and traversals. 363: * 364: * @param node the node 365: */ 366: private void setHead(Node node) { 367: head = node; 368: node.thread = null; 369: node.prev = null; 370: } 371: 372: /** 373: * Wakes up node's successor, if one exists. 374: * 375: * @param node the node 376: */ 377: private void unparkSuccessor(Node node) { 378: /* 379: * Try to clear status in anticipation of signalling. It is 380: * OK if this fails or if status is changed by waiting thread. 381: */ 382: compareAndSetWaitStatus(node, Node.SIGNAL, 0); 383: 384: /* 385: * Thread to unpark is held in successor, which is normally 386: * just the next node. But if cancelled or apparently null, 387: * traverse backwards from tail to find the actual 388: * non-cancelled successor. 389: */ 390: Node s = node.next; 391: if (s == null || s.waitStatus > 0) { 392: s = null; 393: for (Node t = tail; t != null && t != node; t = t.prev) 394: if (t.waitStatus <= 0) 395: s = t; 396: } 397: if (s != null) 398: LockSupport.unpark(s.thread); 399: } 400: 401: /** 402: * Sets head of queue, and checks if successor may be waiting 403: * in shared mode, if so propagating if propagate > 0. 404: * 405: * @param pred the node holding waitStatus for node 406: * @param node the node 407: * @param propagate the return value from a tryAcquireShared 408: */ 409: private void setHeadAndPropagate(Node node, long propagate) { 410: setHead(node); 411: if (propagate > 0 && node.waitStatus != 0) { 412: /* 413: * Don't bother fully figuring out successor. If it 414: * looks null, call unparkSuccessor anyway to be safe. 415: */ 416: Node s = node.next; 417: if (s == null || s.isShared()) 418: unparkSuccessor(node); 419: } 420: } 421: 422: // Utilities for various versions of acquire 423: 424: /** 425: * Cancels an ongoing attempt to acquire. 426: * 427: * @param node the node 428: */ 429: private void cancelAcquire(Node node) { 430: if (node != null) { // Ignore if node doesn't exist 431: node.thread = null; 432: // Can use unconditional write instead of CAS here 433: node.waitStatus = Node.CANCELLED; 434: unparkSuccessor(node); 435: } 436: } 437: 438: /** 439: * Checks and updates status for a node that failed to acquire. 440: * Returns true if thread should block. This is the main signal 441: * control in all acquire loops. Requires that pred == node.prev 442: * 443: * @param pred node's predecessor holding status 444: * @param node the node 445: * @return {@code true} if thread should block 446: */ 447: private static boolean shouldParkAfterFailedAcquire(Node pred, Node node) { 448: int s = pred.waitStatus; 449: if (s < 0) 450: /* 451: * This node has already set status asking a release 452: * to signal it, so it can safely park 453: */ 454: return true; 455: if (s > 0) 456: /* 457: * Predecessor was cancelled. Move up to its predecessor 458: * and indicate retry. 459: */ 460: node.prev = pred.prev; 461: else 462: /* 463: * Indicate that we need a signal, but don't park yet. Caller 464: * will need to retry to make sure it cannot acquire before 465: * parking. 466: */ 467: compareAndSetWaitStatus(pred, 0, Node.SIGNAL); 468: return false; 469: } 470: 471: /** 472: * Convenience method to interrupt current thread. 473: */ 474: private static void selfInterrupt() { 475: Thread.currentThread().interrupt(); 476: } 477: 478: /** 479: * Convenience method to park and then check if interrupted 480: * 481: * @return {@code true} if interrupted 482: */ 483: private final boolean parkAndCheckInterrupt() { 484: LockSupport.park(this); 485: return Thread.interrupted(); 486: } 487: 488: /* 489: * Various flavors of acquire, varying in exclusive/shared and 490: * control modes. Each is mostly the same, but annoyingly 491: * different. Only a little bit of factoring is possible due to 492: * interactions of exception mechanics (including ensuring that we 493: * cancel if tryAcquire throws exception) and other control, at 494: * least not without hurting performance too much. 495: */ 496: 497: /** 498: * Acquires in exclusive uninterruptible mode for thread already in 499: * queue. Used by condition wait methods as well as acquire. 500: * 501: * @param node the node 502: * @param arg the acquire argument 503: * @return {@code true} if interrupted while waiting 504: */ 505: final boolean acquireQueued(final Node node, long arg) { 506: try { 507: boolean interrupted = false; 508: for (;;) { 509: final Node p = node.predecessor(); 510: if (p == head && tryAcquire(arg)) { 511: setHead(node); 512: p.next = null; // help GC 513: return interrupted; 514: } 515: if (shouldParkAfterFailedAcquire(p, node) && 516: parkAndCheckInterrupt()) 517: interrupted = true; 518: } 519: } catch (RuntimeException ex) { 520: cancelAcquire(node); 521: throw ex; 522: } 523: } 524: 525: /** 526: * Acquires in exclusive interruptible mode. 527: * @param arg the acquire argument 528: */ 529: private void doAcquireInterruptibly(long arg) 530: throws InterruptedException { 531: final Node node = addWaiter(Node.EXCLUSIVE); 532: try { 533: for (;;) { 534: final Node p = node.predecessor(); 535: if (p == head && tryAcquire(arg)) { 536: setHead(node); 537: p.next = null; // help GC 538: return; 539: } 540: if (shouldParkAfterFailedAcquire(p, node) && 541: parkAndCheckInterrupt()) 542: break; 543: } 544: } catch (RuntimeException ex) { 545: cancelAcquire(node); 546: throw ex; 547: } 548: // Arrive here only if interrupted 549: cancelAcquire(node); 550: throw new InterruptedException(); 551: } 552: 553: /** 554: * Acquires in exclusive timed mode. 555: * 556: * @param arg the acquire argument 557: * @param nanosTimeout max wait time 558: * @return {@code true} if acquired 559: */ 560: private boolean doAcquireNanos(long arg, long nanosTimeout) 561: throws InterruptedException { 562: long lastTime = System.nanoTime(); 563: final Node node = addWaiter(Node.EXCLUSIVE); 564: try { 565: for (;;) { 566: final Node p = node.predecessor(); 567: if (p == head && tryAcquire(arg)) { 568: setHead(node); 569: p.next = null; // help GC 570: return true; 571: } 572: if (nanosTimeout <= 0) { 573: cancelAcquire(node); 574: return false; 575: } 576: if (nanosTimeout > spinForTimeoutThreshold && 577: shouldParkAfterFailedAcquire(p, node)) 578: LockSupport.parkNanos(this, nanosTimeout); 579: long now = System.nanoTime(); 580: nanosTimeout -= now - lastTime; 581: lastTime = now; 582: if (Thread.interrupted()) 583: break; 584: } 585: } catch (RuntimeException ex) { 586: cancelAcquire(node); 587: throw ex; 588: } 589: // Arrive here only if interrupted 590: cancelAcquire(node); 591: throw new InterruptedException(); 592: } 593: 594: /** 595: * Acquires in shared uninterruptible mode. 596: * @param arg the acquire argument 597: */ 598: private void doAcquireShared(long arg) { 599: final Node node = addWaiter(Node.SHARED); 600: try { 601: boolean interrupted = false; 602: for (;;) { 603: final Node p = node.predecessor(); 604: if (p == head) { 605: long r = tryAcquireShared(arg); 606: if (r >= 0) { 607: setHeadAndPropagate(node, r); 608: p.next = null; // help GC 609: if (interrupted) 610: selfInterrupt(); 611: return; 612: } 613: } 614: if (shouldParkAfterFailedAcquire(p, node) && 615: parkAndCheckInterrupt()) 616: interrupted = true; 617: } 618: } catch (RuntimeException ex) { 619: cancelAcquire(node); 620: throw ex; 621: } 622: } 623: 624: /** 625: * Acquires in shared interruptible mode. 626: * @param arg the acquire argument 627: */ 628: private void doAcquireSharedInterruptibly(long arg) 629: throws InterruptedException { 630: final Node node = addWaiter(Node.SHARED); 631: try { 632: for (;;) { 633: final Node p = node.predecessor(); 634: if (p == head) { 635: long r = tryAcquireShared(arg); 636: if (r >= 0) { 637: setHeadAndPropagate(node, r); 638: p.next = null; // help GC 639: return; 640: } 641: } 642: if (shouldParkAfterFailedAcquire(p, node) && 643: parkAndCheckInterrupt()) 644: break; 645: } 646: } catch (RuntimeException ex) { 647: cancelAcquire(node); 648: throw ex; 649: } 650: // Arrive here only if interrupted 651: cancelAcquire(node); 652: throw new InterruptedException(); 653: } 654: 655: /** 656: * Acquires in shared timed mode. 657: * 658: * @param arg the acquire argument 659: * @param nanosTimeout max wait time 660: * @return {@code true} if acquired 661: */ 662: private boolean doAcquireSharedNanos(long arg, long nanosTimeout) 663: throws InterruptedException { 664: 665: long lastTime = System.nanoTime(); 666: final Node node = addWaiter(Node.SHARED); 667: try { 668: for (;;) { 669: final Node p = node.predecessor(); 670: if (p == head) { 671: long r = tryAcquireShared(arg); 672: if (r >= 0) { 673: setHeadAndPropagate(node, r); 674: p.next = null; // help GC 675: return true; 676: } 677: } 678: if (nanosTimeout <= 0) { 679: cancelAcquire(node); 680: return false; 681: } 682: if (nanosTimeout > spinForTimeoutThreshold && 683: shouldParkAfterFailedAcquire(p, node)) 684: LockSupport.parkNanos(this, nanosTimeout); 685: long now = System.nanoTime(); 686: nanosTimeout -= now - lastTime; 687: lastTime = now; 688: if (Thread.interrupted()) 689: break; 690: } 691: } catch (RuntimeException ex) { 692: cancelAcquire(node); 693: throw ex; 694: } 695: // Arrive here only if interrupted 696: cancelAcquire(node); 697: throw new InterruptedException(); 698: } 699: 700: // Main exported methods 701: 702: /** 703: * Attempts to acquire in exclusive mode. This method should query 704: * if the state of the object permits it to be acquired in the 705: * exclusive mode, and if so to acquire it. 706: * 707: * <p>This method is always invoked by the thread performing 708: * acquire. If this method reports failure, the acquire method 709: * may queue the thread, if it is not already queued, until it is 710: * signalled by a release from some other thread. This can be used 711: * to implement method {@link Lock#tryLock()}. 712: * 713: * <p>The default 714: * implementation throws {@link UnsupportedOperationException}. 715: * 716: * @param arg the acquire argument. This value is always the one 717: * passed to an acquire method, or is the value saved on entry 718: * to a condition wait. The value is otherwise uninterpreted 719: * and can represent anything you like. 720: * @return {@code true} if successful. Upon success, this object has 721: * been acquired. 722: * @throws IllegalMonitorStateException if acquiring would place this 723: * synchronizer in an illegal state. This exception must be 724: * thrown in a consistent fashion for synchronization to work 725: * correctly. 726: * @throws UnsupportedOperationException if exclusive mode is not supported 727: */ 728: protected boolean tryAcquire(long arg) { 729: throw new UnsupportedOperationException(); 730: } 731: 732: /** 733: * Attempts to set the state to reflect a release in exclusive 734: * mode. 735: * 736: * <p>This method is always invoked by the thread performing release. 737: * 738: * <p>The default implementation throws 739: * {@link UnsupportedOperationException}. 740: * 741: * @param arg the release argument. This value is always the one 742: * passed to a release method, or the current state value upon 743: * entry to a condition wait. The value is otherwise 744: * uninterpreted and can represent anything you like. 745: * @return {@code true} if this object is now in a fully released 746: * state, so that any waiting threads may attempt to acquire; 747: * and {@code false} otherwise. 748: * @throws IllegalMonitorStateException if releasing would place this 749: * synchronizer in an illegal state. This exception must be 750: * thrown in a consistent fashion for synchronization to work 751: * correctly. 752: * @throws UnsupportedOperationException if exclusive mode is not supported 753: */ 754: protected boolean tryRelease(long arg) { 755: throw new UnsupportedOperationException(); 756: } 757: 758: /** 759: * Attempts to acquire in shared mode. This method should query if 760: * the state of the object permits it to be acquired in the shared 761: * mode, and if so to acquire it. 762: * 763: * <p>This method is always invoked by the thread performing 764: * acquire. If this method reports failure, the acquire method 765: * may queue the thread, if it is not already queued, until it is 766: * signalled by a release from some other thread. 767: * 768: * <p>The default implementation throws {@link 769: * UnsupportedOperationException}. 770: * 771: * @param arg the acquire argument. This value is always the one 772: * passed to an acquire method, or is the value saved on entry 773: * to a condition wait. The value is otherwise uninterpreted 774: * and can represent anything you like. 775: * @return a negative value on failure; zero if acquisition in shared 776: * mode succeeded but no subsequent shared-mode acquire can 777: * succeed; and a positive value if acquisition in shared 778: * mode succeeded and subsequent shared-mode acquires might 779: * also succeed, in which case a subsequent waiting thread 780: * must check availability. (Support for three different 781: * return values enables this method to be used in contexts 782: * where acquires only sometimes act exclusively.) Upon 783: * success, this object has been acquired. 784: * @throws IllegalMonitorStateException if acquiring would place this 785: * synchronizer in an illegal state. This exception must be 786: * thrown in a consistent fashion for synchronization to work 787: * correctly. 788: * @throws UnsupportedOperationException if shared mode is not supported 789: */ 790: protected long tryAcquireShared(long arg) { 791: throw new UnsupportedOperationException(); 792: } 793: 794: /** 795: * Attempts to set the state to reflect a release in shared mode. 796: * 797: * <p>This method is always invoked by the thread performing release. 798: * 799: * <p>The default implementation throws 800: * {@link UnsupportedOperationException}. 801: * 802: * @param arg the release argument. This value is always the one 803: * passed to a release method, or the current state value upon 804: * entry to a condition wait. The value is otherwise 805: * uninterpreted and can represent anything you like. 806: * @return {@code true} if this release of shared mode may permit a 807: * waiting acquire (shared or exclusive) to succeed; and 808: * {@code false} otherwise 809: * @throws IllegalMonitorStateException if releasing would place this 810: * synchronizer in an illegal state. This exception must be 811: * thrown in a consistent fashion for synchronization to work 812: * correctly. 813: * @throws UnsupportedOperationException if shared mode is not supported 814: */ 815: protected boolean tryReleaseShared(long arg) { 816: throw new UnsupportedOperationException(); 817: } 818: 819: /** 820: * Returns {@code true} if synchronization is held exclusively with 821: * respect to the current (calling) thread. This method is invoked 822: * upon each call to a non-waiting {@link ConditionObject} method. 823: * (Waiting methods instead invoke {@link #release}.) 824: * 825: * <p>The default implementation throws {@link 826: * UnsupportedOperationException}. This method is invoked 827: * internally only within {@link ConditionObject} methods, so need 828: * not be defined if conditions are not used. 829: * 830: * @return {@code true} if synchronization is held exclusively; 831: * {@code false} otherwise 832: * @throws UnsupportedOperationException if conditions are not supported 833: */ 834: protected boolean isHeldExclusively() { 835: throw new UnsupportedOperationException(); 836: } 837: 838: /** 839: * Acquires in exclusive mode, ignoring interrupts. Implemented 840: * by invoking at least once {@link #tryAcquire}, 841: * returning on success. Otherwise the thread is queued, possibly 842: * repeatedly blocking and unblocking, invoking {@link 843: * #tryAcquire} until success. This method can be used 844: * to implement method {@link Lock#lock}. 845: * 846: * @param arg the acquire argument. This value is conveyed to 847: * {@link #tryAcquire} but is otherwise uninterpreted and 848: * can represent anything you like. 849: */ 850: public final void acquire(long arg) { 851: if (!tryAcquire(arg) && 852: acquireQueued(addWaiter(Node.EXCLUSIVE), arg)) 853: selfInterrupt(); 854: } 855: 856: /** 857: * Acquires in exclusive mode, aborting if interrupted. 858: * Implemented by first checking interrupt status, then invoking 859: * at least once {@link #tryAcquire}, returning on 860: * success. Otherwise the thread is queued, possibly repeatedly 861: * blocking and unblocking, invoking {@link #tryAcquire} 862: * until success or the thread is interrupted. This method can be 863: * used to implement method {@link Lock#lockInterruptibly}. 864: * 865: * @param arg the acquire argument. This value is conveyed to 866: * {@link #tryAcquire} but is otherwise uninterpreted and 867: * can represent anything you like. 868: * @throws InterruptedException if the current thread is interrupted 869: */ 870: public final void acquireInterruptibly(long arg) throws InterruptedException { 871: if (Thread.interrupted()) 872: throw new InterruptedException(); 873: if (!tryAcquire(arg)) 874: doAcquireInterruptibly(arg); 875: } 876: 877: /** 878: * Attempts to acquire in exclusive mode, aborting if interrupted, 879: * and failing if the given timeout elapses. Implemented by first 880: * checking interrupt status, then invoking at least once {@link 881: * #tryAcquire}, returning on success. Otherwise, the thread is 882: * queued, possibly repeatedly blocking and unblocking, invoking 883: * {@link #tryAcquire} until success or the thread is interrupted 884: * or the timeout elapses. This method can be used to implement 885: * method {@link Lock#tryLock(long, TimeUnit)}. 886: * 887: * @param arg the acquire argument. This value is conveyed to 888: * {@link #tryAcquire} but is otherwise uninterpreted and 889: * can represent anything you like. 890: * @