Home | History | Annotate | Download | only in concurrent
      1 /*
      2  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
      3  *
      4  * This code is free software; you can redistribute it and/or modify it
      5  * under the terms of the GNU General Public License version 2 only, as
      6  * published by the Free Software Foundation.  Oracle designates this
      7  * particular file as subject to the "Classpath" exception as provided
      8  * by Oracle in the LICENSE file that accompanied this code.
      9  *
     10  * This code is distributed in the hope that it will be useful, but WITHOUT
     11  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
     12  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
     13  * version 2 for more details (a copy is included in the LICENSE file that
     14  * accompanied this code).
     15  *
     16  * You should have received a copy of the GNU General Public License version
     17  * 2 along with this work; if not, write to the Free Software Foundation,
     18  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
     19  *
     20  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
     21  * or visit www.oracle.com if you need additional information or have any
     22  * questions.
     23  */
     24 
     25 /*
     26  * This file is available under and governed by the GNU General Public
     27  * License version 2 only, as published by the Free Software Foundation.
     28  * However, the following notice accompanied the original version of this
     29  * file:
     30  *
     31  * Written by Doug Lea with assistance from members of JCP JSR-166
     32  * Expert Group and released to the public domain, as explained at
     33  * http://creativecommons.org/publicdomain/zero/1.0/
     34  */
     35 
     36 package java.util.concurrent;
     37 
     38 import java.util.Collection;
     39 import java.util.concurrent.locks.AbstractQueuedSynchronizer;
     40 
     41 /**
     42  * A counting semaphore.  Conceptually, a semaphore maintains a set of
     43  * permits.  Each {@link #acquire} blocks if necessary until a permit is
     44  * available, and then takes it.  Each {@link #release} adds a permit,
     45  * potentially releasing a blocking acquirer.
     46  * However, no actual permit objects are used; the {@code Semaphore} just
     47  * keeps a count of the number available and acts accordingly.
     48  *
     49  * <p>Semaphores are often used to restrict the number of threads than can
     50  * access some (physical or logical) resource. For example, here is
     51  * a class that uses a semaphore to control access to a pool of items:
     52  * <pre> {@code
     53  * class Pool {
     54  *   private static final int MAX_AVAILABLE = 100;
     55  *   private final Semaphore available = new Semaphore(MAX_AVAILABLE, true);
     56  *
     57  *   public Object getItem() throws InterruptedException {
     58  *     available.acquire();
     59  *     return getNextAvailableItem();
     60  *   }
     61  *
     62  *   public void putItem(Object x) {
     63  *     if (markAsUnused(x))
     64  *       available.release();
     65  *   }
     66  *
     67  *   // Not a particularly efficient data structure; just for demo
     68  *
     69  *   protected Object[] items = ... whatever kinds of items being managed
     70  *   protected boolean[] used = new boolean[MAX_AVAILABLE];
     71  *
     72  *   protected synchronized Object getNextAvailableItem() {
     73  *     for (int i = 0; i < MAX_AVAILABLE; ++i) {
     74  *       if (!used[i]) {
     75  *          used[i] = true;
     76  *          return items[i];
     77  *       }
     78  *     }
     79  *     return null; // not reached
     80  *   }
     81  *
     82  *   protected synchronized boolean markAsUnused(Object item) {
     83  *     for (int i = 0; i < MAX_AVAILABLE; ++i) {
     84  *       if (item == items[i]) {
     85  *          if (used[i]) {
     86  *            used[i] = false;
     87  *            return true;
     88  *          } else
     89  *            return false;
     90  *       }
     91  *     }
     92  *     return false;
     93  *   }
     94  * }}</pre>
     95  *
     96  * <p>Before obtaining an item each thread must acquire a permit from
     97  * the semaphore, guaranteeing that an item is available for use. When
     98  * the thread has finished with the item it is returned back to the
     99  * pool and a permit is returned to the semaphore, allowing another
    100  * thread to acquire that item.  Note that no synchronization lock is
    101  * held when {@link #acquire} is called as that would prevent an item
    102  * from being returned to the pool.  The semaphore encapsulates the
    103  * synchronization needed to restrict access to the pool, separately
    104  * from any synchronization needed to maintain the consistency of the
    105  * pool itself.
    106  *
    107  * <p>A semaphore initialized to one, and which is used such that it
    108  * only has at most one permit available, can serve as a mutual
    109  * exclusion lock.  This is more commonly known as a <em>binary
    110  * semaphore</em>, because it only has two states: one permit
    111  * available, or zero permits available.  When used in this way, the
    112  * binary semaphore has the property (unlike many {@link java.util.concurrent.locks.Lock}
    113  * implementations), that the &quot;lock&quot; can be released by a
    114  * thread other than the owner (as semaphores have no notion of
    115  * ownership).  This can be useful in some specialized contexts, such
    116  * as deadlock recovery.
    117  *
    118  * <p>The constructor for this class optionally accepts a
    119  * <em>fairness</em> parameter. When set false, this class makes no
    120  * guarantees about the order in which threads acquire permits. In
    121  * particular, <em>barging</em> is permitted, that is, a thread
    122  * invoking {@link #acquire} can be allocated a permit ahead of a
    123  * thread that has been waiting - logically the new thread places itself at
    124  * the head of the queue of waiting threads. When fairness is set true, the
    125  * semaphore guarantees that threads invoking any of the {@link
    126  * #acquire() acquire} methods are selected to obtain permits in the order in
    127  * which their invocation of those methods was processed
    128  * (first-in-first-out; FIFO). Note that FIFO ordering necessarily
    129  * applies to specific internal points of execution within these
    130  * methods.  So, it is possible for one thread to invoke
    131  * {@code acquire} before another, but reach the ordering point after
    132  * the other, and similarly upon return from the method.
    133  * Also note that the untimed {@link #tryAcquire() tryAcquire} methods do not
    134  * honor the fairness setting, but will take any permits that are
    135  * available.
    136  *
    137  * <p>Generally, semaphores used to control resource access should be
    138  * initialized as fair, to ensure that no thread is starved out from
    139  * accessing a resource. When using semaphores for other kinds of
    140  * synchronization control, the throughput advantages of non-fair
    141  * ordering often outweigh fairness considerations.
    142  *
    143  * <p>This class also provides convenience methods to {@link
    144  * #acquire(int) acquire} and {@link #release(int) release} multiple
    145  * permits at a time. These methods are generally more efficient and
    146  * effective than loops. However, they do not establish any preference
    147  * order. For example, if thread A invokes {@code s.acquire(3}) and
    148  * thread B invokes {@code s.acquire(2)}, and two permits become
    149  * available, then there is no guarantee that thread B will obtain
    150  * them unless its acquire came first and Semaphore {@code s} is in
    151  * fair mode.
    152  *
    153  * <p>Memory consistency effects: Actions in a thread prior to calling
    154  * a "release" method such as {@code release()}
    155  * <a href="package-summary.html#MemoryVisibility"><i>happen-before</i></a>
    156  * actions following a successful "acquire" method such as {@code acquire()}
    157  * in another thread.
    158  *
    159  * @since 1.5
    160  * @author Doug Lea
    161  */
    162 public class Semaphore implements java.io.Serializable {
    163     private static final long serialVersionUID = -3222578661600680210L;
    164     /** All mechanics via AbstractQueuedSynchronizer subclass */
    165     private final Sync sync;
    166 
    167     /**
    168      * Synchronization implementation for semaphore.  Uses AQS state
    169      * to represent permits. Subclassed into fair and nonfair
    170      * versions.
    171      */
    172     abstract static class Sync extends AbstractQueuedSynchronizer {
    173         private static final long serialVersionUID = 1192457210091910933L;
    174 
    175         Sync(int permits) {
    176             setState(permits);
    177         }
    178 
    179         final int getPermits() {
    180             return getState();
    181         }
    182 
    183         final int nonfairTryAcquireShared(int acquires) {
    184             for (;;) {
    185                 int available = getState();
    186                 int remaining = available - acquires;
    187                 if (remaining < 0 ||
    188                     compareAndSetState(available, remaining))
    189                     return remaining;
    190             }
    191         }
    192 
    193         protected final boolean tryReleaseShared(int releases) {
    194             for (;;) {
    195                 int current = getState();
    196                 int next = current + releases;
    197                 if (next < current) // overflow
    198                     throw new Error("Maximum permit count exceeded");
    199                 if (compareAndSetState(current, next))
    200                     return true;
    201             }
    202         }
    203 
    204         final void reducePermits(int reductions) {
    205             for (;;) {
    206                 int current = getState();
    207                 int next = current - reductions;
    208                 if (next > current) // underflow
    209                     throw new Error("Permit count underflow");
    210                 if (compareAndSetState(current, next))
    211                     return;
    212             }
    213         }
    214 
    215         final int drainPermits() {
    216             for (;;) {
    217                 int current = getState();
    218                 if (current == 0 || compareAndSetState(current, 0))
    219                     return current;
    220             }
    221         }
    222     }
    223 
    224     /**
    225      * NonFair version
    226      */
    227     static final class NonfairSync extends Sync {
    228         private static final long serialVersionUID = -2694183684443567898L;
    229 
    230         NonfairSync(int permits) {
    231             super(permits);
    232         }
    233 
    234         protected int tryAcquireShared(int acquires) {
    235             return nonfairTryAcquireShared(acquires);
    236         }
    237     }
    238 
    239     /**
    240      * Fair version
    241      */
    242     static final class FairSync extends Sync {
    243         private static final long serialVersionUID = 2014338818796000944L;
    244 
    245         FairSync(int permits) {
    246             super(permits);
    247         }
    248 
    249         protected int tryAcquireShared(int acquires) {
    250             for (;;) {
    251                 if (hasQueuedPredecessors())
    252                     return -1;
    253                 int available = getState();
    254                 int remaining = available - acquires;
    255                 if (remaining < 0 ||
    256                     compareAndSetState(available, remaining))
    257                     return remaining;
    258             }
    259         }
    260     }
    261 
    262     /**
    263      * Creates a {@code Semaphore} with the given number of
    264      * permits and nonfair fairness setting.
    265      *
    266      * @param permits the initial number of permits available.
    267      *        This value may be negative, in which case releases
    268      *        must occur before any acquires will be granted.
    269      */
    270     public Semaphore(int permits) {
    271         sync = new NonfairSync(permits);
    272     }
    273 
    274     /**
    275      * Creates a {@code Semaphore} with the given number of
    276      * permits and the given fairness setting.
    277      *
    278      * @param permits the initial number of permits available.
    279      *        This value may be negative, in which case releases
    280      *        must occur before any acquires will be granted.
    281      * @param fair {@code true} if this semaphore will guarantee
    282      *        first-in first-out granting of permits under contention,
    283      *        else {@code false}
    284      */
    285     public Semaphore(int permits, boolean fair) {
    286         sync = fair ? new FairSync(permits) : new NonfairSync(permits);
    287     }
    288 
    289     /**
    290      * Acquires a permit from this semaphore, blocking until one is
    291      * available, or the thread is {@linkplain Thread#interrupt interrupted}.
    292      *
    293      * <p>Acquires a permit, if one is available and returns immediately,
    294      * reducing the number of available permits by one.
    295      *
    296      * <p>If no permit is available then the current thread becomes
    297      * disabled for thread scheduling purposes and lies dormant until
    298      * one of two things happens:
    299      * <ul>
    300      * <li>Some other thread invokes the {@link #release} method for this
    301      * semaphore and the current thread is next to be assigned a permit; or
    302      * <li>Some other thread {@linkplain Thread#interrupt interrupts}
    303      * the current thread.
    304      * </ul>
    305      *
    306      * <p>If the current thread:
    307      * <ul>
    308      * <li>has its interrupted status set on entry to this method; or
    309      * <li>is {@linkplain Thread#interrupt interrupted} while waiting
    310      * for a permit,
    311      * </ul>
    312      * then {@link InterruptedException} is thrown and the current thread's
    313      * interrupted status is cleared.
    314      *
    315      * @throws InterruptedException if the current thread is interrupted
    316      */
    317     public void acquire() throws InterruptedException {
    318         sync.acquireSharedInterruptibly(1);
    319     }
    320 
    321     /**
    322      * Acquires a permit from this semaphore, blocking until one is
    323      * available.
    324      *
    325      * <p>Acquires a permit, if one is available and returns immediately,
    326      * reducing the number of available permits by one.
    327      *
    328      * <p>If no permit is available then the current thread becomes
    329      * disabled for thread scheduling purposes and lies dormant until
    330      * some other thread invokes the {@link #release} method for this
    331      * semaphore and the current thread is next to be assigned a permit.
    332      *
    333      * <p>If the current thread is {@linkplain Thread#interrupt interrupted}
    334      * while waiting for a permit then it will continue to wait, but the
    335      * time at which the thread is assigned a permit may change compared to
    336      * the time it would have received the permit had no interruption
    337      * occurred.  When the thread does return from this method its interrupt
    338      * status will be set.
    339      */
    340     public void acquireUninterruptibly() {
    341         sync.acquireShared(1);
    342     }
    343 
    344     /**
    345      * Acquires a permit from this semaphore, only if one is available at the
    346      * time of invocation.
    347      *
    348      * <p>Acquires a permit, if one is available and returns immediately,
    349      * with the value {@code true},
    350      * reducing the number of available permits by one.
    351      *
    352      * <p>If no permit is available then this method will return
    353      * immediately with the value {@code false}.
    354      *
    355      * <p>Even when this semaphore has been set to use a
    356      * fair ordering policy, a call to {@code tryAcquire()} <em>will</em>
    357      * immediately acquire a permit if one is available, whether or not
    358      * other threads are currently waiting.
    359      * This &quot;barging&quot; behavior can be useful in certain
    360      * circumstances, even though it breaks fairness. If you want to honor
    361      * the fairness setting, then use
    362      * {@link #tryAcquire(long, TimeUnit) tryAcquire(0, TimeUnit.SECONDS) }
    363      * which is almost equivalent (it also detects interruption).
    364      *
    365      * @return {@code true} if a permit was acquired and {@code false}
    366      *         otherwise
    367      */
    368     public boolean tryAcquire() {
    369         return sync.nonfairTryAcquireShared(1) >= 0;
    370     }
    371 
    372     /**
    373      * Acquires a permit from this semaphore, if one becomes available
    374      * within the given waiting time and the current thread has not
    375      * been {@linkplain Thread#interrupt interrupted}.
    376      *
    377      * <p>Acquires a permit, if one is available and returns immediately,
    378      * with the value {@code true},
    379      * reducing the number of available permits by one.
    380      *
    381      * <p>If no permit is available then the current thread becomes
    382      * disabled for thread scheduling purposes and lies dormant until
    383      * one of three things happens:
    384      * <ul>
    385      * <li>Some other thread invokes the {@link #release} method for this
    386      * semaphore and the current thread is next to be assigned a permit; or
    387      * <li>Some other thread {@linkplain Thread#interrupt interrupts}
    388      * the current thread; or
    389      * <li>The specified waiting time elapses.
    390      * </ul>
    391      *
    392      * <p>If a permit is acquired then the value {@code true} is returned.
    393      *
    394      * <p>If the current thread:
    395      * <ul>
    396      * <li>has its interrupted status set on entry to this method; or
    397      * <li>is {@linkplain Thread#interrupt interrupted} while waiting
    398      * to acquire a permit,
    399      * </ul>
    400      * then {@link InterruptedException} is thrown and the current thread's
    401      * interrupted status is cleared.
    402      *
    403      * <p>If the specified waiting time elapses then the value {@code false}
    404      * is returned.  If the time is less than or equal to zero, the method
    405      * will not wait at all.
    406      *
    407      * @param timeout the maximum time to wait for a permit
    408      * @param unit the time unit of the {@code timeout} argument
    409      * @return {@code true} if a permit was acquired and {@code false}
    410      *         if the waiting time elapsed before a permit was acquired
    411      * @throws InterruptedException if the current thread is interrupted
    412      */
    413     public boolean tryAcquire(long timeout, TimeUnit unit)
    414         throws InterruptedException {
    415         return sync.tryAcquireSharedNanos(1, unit.toNanos(timeout));
    416     }
    417 
    418     /**
    419      * Releases a permit, returning it to the semaphore.
    420      *
    421      * <p>Releases a permit, increasing the number of available permits by
    422      * one.  If any threads are trying to acquire a permit, then one is
    423      * selected and given the permit that was just released.  That thread
    424      * is (re)enabled for thread scheduling purposes.
    425      *
    426      * <p>There is no requirement that a thread that releases a permit must
    427      * have acquired that permit by calling {@link #acquire}.
    428      * Correct usage of a semaphore is established by programming convention
    429      * in the application.
    430      */
    431     public void release() {
    432         sync.releaseShared(1);
    433     }
    434 
    435     /**
    436      * Acquires the given number of permits from this semaphore,
    437      * blocking until all are available,
    438      * or the thread is {@linkplain Thread#interrupt interrupted}.
    439      *
    440      * <p>Acquires the given number of permits, if they are available,
    441      * and returns immediately, reducing the number of available permits
    442      * by the given amount. This method has the same effect as the
    443      * loop {@code for (int i = 0; i < permits; ++i) acquire();} except
    444      * that it atomically acquires the permits all at once:
    445      *
    446      * <p>If insufficient permits are available then the current thread becomes
    447      * disabled for thread scheduling purposes and lies dormant until
    448      * one of two things happens:
    449      * <ul>
    450      * <li>Some other thread invokes one of the {@link #release() release}
    451      * methods for this semaphore and the current thread is next to be assigned
    452      * permits and the number of available permits satisfies this request; or
    453      * <li>Some other thread {@linkplain Thread#interrupt interrupts}
    454      * the current thread.
    455      * </ul>
    456      *
    457      * <p>If the current thread:
    458      * <ul>
    459      * <li>has its interrupted status set on entry to this method; or
    460      * <li>is {@linkplain Thread#interrupt interrupted} while waiting
    461      * for a permit,
    462      * </ul>
    463      * then {@link InterruptedException} is thrown and the current thread's
    464      * interrupted status is cleared.
    465      * Any permits that were to be assigned to this thread are instead
    466      * assigned to other threads trying to acquire permits, as if
    467      * permits had been made available by a call to {@link #release()}.
    468      *
    469      * @param permits the number of permits to acquire
    470      * @throws InterruptedException if the current thread is interrupted
    471      * @throws IllegalArgumentException if {@code permits} is negative
    472      */
    473     public void acquire(int permits) throws InterruptedException {
    474         if (permits < 0) throw new IllegalArgumentException();
    475         sync.acquireSharedInterruptibly(permits);
    476     }
    477 
    478     /**
    479      * Acquires the given number of permits from this semaphore,
    480      * blocking until all are available.
    481      *
    482      * <p>Acquires the given number of permits, if they are available,
    483      * and returns immediately, reducing the number of available permits
    484      * by the given amount. This method has the same effect as the
    485      * loop {@code for (int i = 0; i < permits; ++i) acquireUninterruptibly();}
    486      * except that it atomically acquires the permits all at once:
    487      *
    488      * <p>If insufficient permits are available then the current thread becomes
    489      * disabled for thread scheduling purposes and lies dormant until
    490      * some other thread invokes one of the {@link #release() release}
    491      * methods for this semaphore and the current thread is next to be assigned
    492      * permits and the number of available permits satisfies this request.
    493      *
    494      * <p>If the current thread is {@linkplain Thread#interrupt interrupted}
    495      * while waiting for permits then it will continue to wait and its
    496      * position in the queue is not affected.  When the thread does return
    497      * from this method its interrupt status will be set.
    498      *
    499      * @param permits the number of permits to acquire
    500      * @throws IllegalArgumentException if {@code permits} is negative
    501      */
    502     public void acquireUninterruptibly(int permits) {
    503         if (permits < 0) throw new IllegalArgumentException();
    504         sync.acquireShared(permits);
    505     }
    506 
    507     /**
    508      * Acquires the given number of permits from this semaphore, only
    509      * if all are available at the time of invocation.
    510      *
    511      * <p>Acquires the given number of permits, if they are available, and
    512      * returns immediately, with the value {@code true},
    513      * reducing the number of available permits by the given amount.
    514      *
    515      * <p>If insufficient permits are available then this method will return
    516      * immediately with the value {@code false} and the number of available
    517      * permits is unchanged.
    518      *
    519      * <p>Even when this semaphore has been set to use a fair ordering
    520      * policy, a call to {@code tryAcquire} <em>will</em>
    521      * immediately acquire a permit if one is available, whether or
    522      * not other threads are currently waiting.  This
    523      * &quot;barging&quot; behavior can be useful in certain
    524      * circumstances, even though it breaks fairness. If you want to
    525      * honor the fairness setting, then use {@link #tryAcquire(int,
    526      * long, TimeUnit) tryAcquire(permits, 0, TimeUnit.SECONDS) }
    527      * which is almost equivalent (it also detects interruption).
    528      *
    529      * @param permits the number of permits to acquire
    530      * @return {@code true} if the permits were acquired and
    531      *         {@code false} otherwise
    532      * @throws IllegalArgumentException if {@code permits} is negative
    533      */
    534     public boolean tryAcquire(int permits) {
    535         if (permits < 0) throw new IllegalArgumentException();
    536         return sync.nonfairTryAcquireShared(permits) >= 0;
    537     }
    538 
    539     /**
    540      * Acquires the given number of permits from this semaphore, if all
    541      * become available within the given waiting time and the current
    542      * thread has not been {@linkplain Thread#interrupt interrupted}.
    543      *
    544      * <p>Acquires the given number of permits, if they are available and
    545      * returns immediately, with the value {@code true},
    546      * reducing the number of available permits by the given amount.
    547      *
    548      * <p>If insufficient permits are available then
    549      * the current thread becomes disabled for thread scheduling
    550      * purposes and lies dormant until one of three things happens:
    551      * <ul>
    552      * <li>Some other thread invokes one of the {@link #release() release}
    553      * methods for this semaphore and the current thread is next to be assigned
    554      * permits and the number of available permits satisfies this request; or
    555      * <li>Some other thread {@linkplain Thread#interrupt interrupts}
    556      * the current thread; or
    557      * <li>The specified waiting time elapses.
    558      * </ul>
    559      *
    560      * <p>If the permits are acquired then the value {@code true} is returned.
    561      *
    562      * <p>If the current thread:
    563      * <ul>
    564      * <li>has its interrupted status set on entry to this method; or
    565      * <li>is {@linkplain Thread#interrupt interrupted} while waiting
    566      * to acquire the permits,
    567      * </ul>
    568      * then {@link InterruptedException} is thrown and the current thread's
    569      * interrupted status is cleared.
    570      * Any permits that were to be assigned to this thread, are instead
    571      * assigned to other threads trying to acquire permits, as if
    572      * the permits had been made available by a call to {@link #release()}.
    573      *
    574      * <p>If the specified waiting time elapses then the value {@code false}
    575      * is returned.  If the time is less than or equal to zero, the method
    576      * will not wait at all.  Any permits that were to be assigned to this
    577      * thread, are instead assigned to other threads trying to acquire
    578      * permits, as if the permits had been made available by a call to
    579      * {@link #release()}.
    580      *
    581      * @param permits the number of permits to acquire
    582      * @param timeout the maximum time to wait for the permits
    583      * @param unit the time unit of the {@code timeout} argument
    584      * @return {@code true} if all permits were acquired and {@code false}
    585      *         if the waiting time elapsed before all permits were acquired
    586      * @throws InterruptedException if the current thread is interrupted
    587      * @throws IllegalArgumentException if {@code permits} is negative
    588      */
    589     public boolean tryAcquire(int permits, long timeout, TimeUnit unit)
    590         throws InterruptedException {
    591         if (permits < 0) throw new IllegalArgumentException();
    592         return sync.tryAcquireSharedNanos(permits, unit.toNanos(timeout));
    593     }
    594 
    595     /**
    596      * Releases the given number of permits, returning them to the semaphore.
    597      *
    598      * <p>Releases the given number of permits, increasing the number of
    599      * available permits by that amount.
    600      * If any threads are trying to acquire permits, then one thread
    601      * is selected and given the permits that were just released.
    602      * If the number of available permits satisfies that thread's request
    603      * then that thread is (re)enabled for thread scheduling purposes;
    604      * otherwise the thread will wait until sufficient permits are available.
    605      * If there are still permits available
    606      * after this thread's request has been satisfied, then those permits
    607      * are assigned in turn to other threads trying to acquire permits.
    608      *
    609      * <p>There is no requirement that a thread that releases a permit must
    610      * have acquired that permit by calling {@link Semaphore#acquire acquire}.
    611      * Correct usage of a semaphore is established by programming convention
    612      * in the application.
    613      *
    614      * @param permits the number of permits to release
    615      * @throws IllegalArgumentException if {@code permits} is negative
    616      */
    617     public void release(int permits) {
    618         if (permits < 0) throw new IllegalArgumentException();
    619         sync.releaseShared(permits);
    620     }
    621 
    622     /**
    623      * Returns the current number of permits available in this semaphore.
    624      *
    625      * <p>This method is typically used for debugging and testing purposes.
    626      *
    627      * @return the number of permits available in this semaphore
    628      */
    629     public int availablePermits() {
    630         return sync.getPermits();
    631     }
    632 
    633     /**
    634      * Acquires and returns all permits that are immediately available.
    635      *
    636      * @return the number of permits acquired
    637      */
    638     public int drainPermits() {
    639         return sync.drainPermits();
    640     }
    641 
    642     /**
    643      * Shrinks the number of available permits by the indicated
    644      * reduction. This method can be useful in subclasses that use
    645      * semaphores to track resources that become unavailable. This
    646      * method differs from {@code acquire} in that it does not block
    647      * waiting for permits to become available.
    648      *
    649      * @param reduction the number of permits to remove
    650      * @throws IllegalArgumentException if {@code reduction} is negative
    651      */
    652     protected void reducePermits(int reduction) {
    653         if (reduction < 0) throw new IllegalArgumentException();
    654         sync.reducePermits(reduction);
    655     }
    656 
    657     /**
    658      * Returns {@code true} if this semaphore has fairness set true.
    659      *
    660      * @return {@code true} if this semaphore has fairness set true
    661      */
    662     public boolean isFair() {
    663         return sync instanceof FairSync;
    664     }
    665 
    666     /**
    667      * Queries whether any threads are waiting to acquire. Note that
    668      * because cancellations may occur at any time, a {@code true}
    669      * return does not guarantee that any other thread will ever
    670      * acquire.  This method is designed primarily for use in
    671      * monitoring of the system state.
    672      *
    673      * @return {@code true} if there may be other threads waiting to
    674      *         acquire the lock
    675      */
    676     public final boolean hasQueuedThreads() {
    677         return sync.hasQueuedThreads();
    678     }
    679 
    680     /**
    681      * Returns an estimate of the number of threads waiting to acquire.
    682      * The value is only an estimate because the number of threads may
    683      * change dynamically while this method traverses internal data
    684      * structures.  This method is designed for use in monitoring
    685      * system state, not for synchronization control.
    686      *
    687      * @return the estimated number of threads waiting for this lock
    688      */
    689     public final int getQueueLength() {
    690         return sync.getQueueLength();
    691     }
    692 
    693     /**
    694      * Returns a collection containing threads that may be waiting to acquire.
    695      * Because the actual set of threads may change dynamically while
    696      * constructing this result, the returned collection is only a best-effort
    697      * estimate.  The elements of the returned collection are in no particular
    698      * order.  This method is designed to facilitate construction of
    699      * subclasses that provide more extensive monitoring facilities.
    700      *
    701      * @return the collection of threads
    702      */
    703     protected Collection<Thread> getQueuedThreads() {
    704         return sync.getQueuedThreads();
    705     }
    706 
    707     /**
    708      * Returns a string identifying this semaphore, as well as its state.
    709      * The state, in brackets, includes the String {@code "Permits ="}
    710      * followed by the number of permits.
    711      *
    712      * @return a string identifying this semaphore, as well as its state
    713      */
    714     public String toString() {
    715         return super.toString() + "[Permits = " + sync.getPermits() + "]";
    716     }
    717 }
    718