--- title: ä»ReentrantLockçå®ç°çAQSçåçååºç¨ category: Java tag: - Javaå¹¶å --- > æ¬æè½¬è½½èªï¼https://tech.meituan.com/2019/12/05/aqs-theory-and-apply.html > > ä½è ï¼ç¾å¢ææ¯å¢é ## åè¨ Javaä¸ç大é¨ååæ¥ç±»ï¼LockãSemaphoreãReentrantLockçï¼é½æ¯åºäºAbstractQueuedSynchronizerï¼ç®ç§°ä¸ºAQSï¼å®ç°çãAQSæ¯ä¸ç§æä¾äºååå¼ç®¡çåæ¥ç¶æãé»å¡åå¤é线ç¨åè½ä»¥åé忍¡åçç®åæ¡æ¶ãæ¬æä¼ä»åºç¨å±éæ¸æ·±å ¥å°åçå±ï¼å¹¶éè¿ReentrantLockçåºæ¬ç¹æ§åReentrantLockä¸AQSçå ³èï¼æ¥æ·±å ¥è§£è¯»AQSç¸å ³ç¬å éçç¥è¯ç¹ï¼åæ¶éåé®ççæ¨¡å¼æ¥å¸®å©å¤§å®¶çè§£AQSãç±äºç¯å¹ åå ï¼æ¬ç¯æç« 主è¦éè¿°AQSä¸ç¬å éçé»è¾åSync Queueï¼ä¸è®²è¿°å å«å ±äº«éåCondition Queueçé¨åï¼æ¬ç¯æç« æ ¸å¿ä¸ºAQSåçåæï¼åªæ¯ç®åä»ç»äºReentrantLockï¼æå ´è¶£åå¦å¯ä»¥é 读ä¸ä¸ReentrantLockçæºç ï¼ã ## 1 ReentrantLock ### 1.1 ReentrantLockç¹æ§æ¦è§ ReentrantLockææä¸ºå¯éå ¥éï¼æçæ¯ä¸ä¸ªçº¿ç¨è½å¤å¯¹ä¸ä¸ªä¸´çèµæºéå¤å éã为äºå¸®å©å¤§å®¶æ´å¥½å°çè§£ReentrantLockçç¹æ§ï¼æä»¬å å°ReentrantLockè·å¸¸ç¨çSynchronizedè¿è¡æ¯è¾ï¼å ¶ç¹æ§å¦ä¸ï¼èè²é¨å为æ¬ç¯æç« 主è¦åæçç¹ï¼ï¼  ä¸é¢éè¿ä¼ªä»£ç ï¼è¿è¡æ´å ç´è§çæ¯è¾ï¼ ```java // **************************Synchronizedçä½¿ç¨æ¹å¼************************** // 1.ç¨äºä»£ç å synchronized (this) {} // 2.ç¨äºå¯¹è±¡ synchronized (object) {} // 3.ç¨äºæ¹æ³ public synchronized void test () {} // 4.å¯éå ¥ for (int i = 0; i < 100; i++) { synchronized (this) {} } // **************************ReentrantLockçä½¿ç¨æ¹å¼************************** public void test () throw Exception { // 1.åå§åéæ©å ¬å¹³éãéå ¬å¹³é ReentrantLock lock = new ReentrantLock(true); // 2.å¯ç¨äºä»£ç å lock.lock(); try { try { // 3.æ¯æå¤ç§å éæ¹å¼ï¼æ¯è¾çµæ´»; å ·æå¯éå ¥ç¹æ§ if(lock.tryLock(100, TimeUnit.MILLISECONDS)){ } } finally { // 4.æå¨éæ¾é lock.unlock() } } finally { lock.unlock(); } } ``` ### 1.2 ReentrantLockä¸AQSçå ³è éè¿ä¸ææä»¬å·²ç»äºè§£ï¼ReentrantLockæ¯æå ¬å¹³éåéå ¬å¹³éï¼å ³äºå ¬å¹³éåéå ¬å¹³éçåçåæï¼å¯åèã[ä¸å¯ä¸è¯´çJavaâéâäº](https://mp.weixin.qq.com/s?__biz=MjM5NjQ5MTI5OA==&mid=2651749434&idx=3&sn=5ffa63ad47fe166f2f1a9f604ed10091&chksm=bd12a5778a652c61509d9e718ab086ff27ad8768586ea9b38c3dcf9e017a8e49bcae3df9bcc8&scene=38#wechat_redirect)ãï¼ï¼å¹¶ä¸ReentrantLockçåºå±å°±æ¯ç±AQSæ¥å®ç°çãé£ä¹ReentrantLockæ¯å¦ä½éè¿å ¬å¹³éåéå ¬å¹³éä¸AQSå ³èèµ·æ¥å¢ï¼ æä»¬çéä»è¿ä¸¤è çå éè¿ç¨æ¥çè§£ä¸ä¸å®ä»¬ä¸AQSä¹é´çå ³ç³»ï¼å éè¿ç¨ä¸ä¸AQSçå ³èæ¯è¾ææ¾ï¼è§£éæµç¨åç»ä¼ä»ç»ï¼ã éå ¬å¹³éæºç ä¸çå éæµç¨å¦ä¸ï¼ ```java // java.util.concurrent.locks.ReentrantLock#NonfairSync // éå ¬å¹³é static final class NonfairSync extends Sync { ... final void lock() { if (compareAndSetState(0, 1)) setExclusiveOwnerThread(Thread.currentThread()); else acquire(1); } ... } ``` è¿å代ç çå«ä¹ä¸ºï¼ - è¥éè¿CAS设置åéStateï¼åæ¥ç¶æï¼æåï¼ä¹å°±æ¯è·åéæåï¼åå°å½å线ç¨è®¾ç½®ä¸ºç¬å 线ç¨ã - è¥éè¿CAS设置åéStateï¼åæ¥ç¶æï¼å¤±è´¥ï¼ä¹å°±æ¯è·åé失败ï¼åè¿å ¥Acquireæ¹æ³è¿è¡åç»å¤çã ç¬¬ä¸æ¥å¾å¥½çè§£ï¼ä½ç¬¬äºæ¥è·åé失败åï¼åç»çå¤ççç¥æ¯æä¹æ ·çå¢ï¼è¿åå¯è½ä¼æä»¥ä¸æèï¼ - æä¸ªçº¿ç¨è·åé失败çåç»æµç¨æ¯ä»ä¹å¢ï¼æä»¥ä¸ä¸¤ç§å¯è½ï¼ (1) å°å½å线ç¨è·éç»æè®¾ç½®ä¸ºå¤±è´¥ï¼è·åéæµç¨ç»æãè¿ç§è®¾è®¡ä¼æå¤§éä½ç³»ç»çå¹¶å度ï¼å¹¶ä¸æ»¡è¶³æä»¬å®é çéæ±ãæä»¥å°±éè¦ä¸é¢è¿ç§æµç¨ï¼ä¹å°±æ¯AQSæ¡æ¶çå¤çæµç¨ã (2) åå¨æç§æéçåæºå¶ï¼çº¿ç¨ç»§ç»çå¾ ï¼ä»ç¶ä¿çè·åéçå¯è½ï¼è·åéæµç¨ä»å¨ç»§ç»ã - 对äºé®é¢1ç第äºç§æ åµï¼æ¢ç¶è¯´å°äºæéçåæºå¶ï¼é£ä¹å°±ä¸å®ä¼ææç§éåå½¢æï¼è¿æ ·çé忝ä»ä¹æ°æ®ç»æå¢ï¼ - å¤äºæéçåæºå¶ä¸ç线ç¨ï¼ä»ä¹æ¶åå¯ä»¥ææºä¼è·åéå¢ï¼ - 妿å¤äºæéçåæºå¶ä¸ç线ç¨ä¸ç´æ æ³è·åéï¼è¿æ¯éè¦ä¸ç´çå¾ åï¼è¿æ¯æå«ççç¥æ¥è§£å³è¿ä¸é®é¢ï¼ 带çéå ¬å¹³éçè¿äºé®é¢ï¼åçä¸å ¬å¹³éæºç ä¸è·éçæ¹å¼ï¼ ``` // java.util.concurrent.locks.ReentrantLock#FairSync static final class FairSync extends Sync { ... final void lock() { acquire(1); } ... } ``` çå°è¿å代ç ï¼æä»¬å¯è½ä¼åå¨è¿ç§çé®ï¼Lock彿°éè¿Acquireæ¹æ³è¿è¡å éï¼ä½æ¯å ·ä½æ¯å¦ä½å éçå¢ï¼ ç»åå ¬å¹³éåéå ¬å¹³éçå éæµç¨ï¼è½ç¶æµç¨ä¸æä¸å®çä¸åï¼ä½æ¯é½è°ç¨äºAcquireæ¹æ³ï¼èAcquireæ¹æ³æ¯FairSyncåUnfairSyncçç¶ç±»AQSä¸çæ ¸å¿æ¹æ³ã 对äºä¸è¾¹æå°çé®é¢ï¼å ¶å®å¨ReentrantLockç±»æºç ä¸é½æ æ³è§£çï¼èè¿äºé®é¢ççæ¡ï¼é½æ¯ä½äºAcquireæ¹æ³æå¨çç±»AbstractQueuedSynchronizerä¸ï¼ä¹å°±æ¯æ¬æçæ ¸å¿ââAQSãä¸é¢æä»¬ä¼å¯¹AQS以åReentrantLockåAQSçå ³èå详ç»ä»ç»ï¼ç¸å ³é®é¢çæ¡ä¼å¨2.3.5å°èä¸è§£çï¼ã ## 2 AQS é¦å ï¼æä»¬éè¿ä¸é¢çæ¶æå¾æ¥æ´ä½äºè§£ä¸ä¸AQSæ¡æ¶ï¼  - ä¸å¾ä¸æé¢è²ç为Methodï¼æ é¢è²ç为Attributionã - æ»çæ¥è¯´ï¼AQSæ¡æ¶å ±å为äºå±ï¼èªä¸èä¸ç±æµ å ¥æ·±ï¼ä»AQS坹夿´é²çAPIå°åºå±åºç¡æ°æ®ã - 彿èªå®ä¹åæ¥å¨æ¥å ¥æ¶ï¼åªééå第ä¸å±æéè¦çé¨åæ¹æ³å³å¯ï¼ä¸éè¦å ³æ³¨åºå±å ·ä½çå®ç°æµç¨ãå½èªå®ä¹åæ¥å¨è¿è¡å éæè è§£éæä½æ¶ï¼å ç»è¿ç¬¬ä¸å±çAPIè¿å ¥AQSå 鍿¹æ³ï¼ç¶åç»è¿ç¬¬äºå±è¿è¡éçè·åï¼æ¥ç对äºè·åéå¤±è´¥çæµç¨ï¼è¿å ¥ç¬¬ä¸å±å第åå±ççå¾ éåå¤çï¼èè¿äºå¤çæ¹å¼åä¾èµäºç¬¬äºå±çåºç¡æ°æ®æä¾å±ã ä¸é¢æä»¬ä¼ä»æ´ä½å°ç»èï¼ä»æµç¨å°æ¹æ³éä¸åæAQSæ¡æ¶ï¼ä¸»è¦åæè¿ç¨å¦ä¸ï¼  ### 2.1 åçæ¦è§ AQSæ ¸å¿ææ³æ¯ï¼å¦æè¢«è¯·æ±çå ±äº«èµæºç©ºé²ï¼é£ä¹å°±å°å½å请æ±èµæºç线ç¨è®¾ç½®ä¸ºææçå·¥ä½çº¿ç¨ï¼å°å ±äº«èµæºè®¾ç½®ä¸ºéå®ç¶æï¼å¦æå ±äº«èµæºè¢«å ç¨ï¼å°±éè¦ä¸å®çé»å¡çå¾ å¤éæºå¶æ¥ä¿è¯éåé ãè¿ä¸ªæºå¶ä¸»è¦ç¨çæ¯CLHéåçåä½å®ç°çï¼å°ææ¶è·åä¸å°éç线ç¨å å ¥å°éåä¸ã CLHï¼CraigãLandin and Hagerstenéåï¼æ¯ååé¾è¡¨ï¼AQSä¸çé忝CLHåä½çèæååéåï¼FIFOï¼ï¼AQSæ¯éè¿å°æ¯æ¡è¯·æ±å ±äº«èµæºç线ç¨å°è£ æä¸ä¸ªèç¹æ¥å®ç°éçåé ã 主è¦åçå¾å¦ä¸ï¼  AQS使ç¨ä¸ä¸ªVolatileçintç±»åçæååéæ¥è¡¨ç¤ºåæ¥ç¶æï¼éè¿å ç½®çFIFOéåæ¥å®æèµæºè·åçæéå·¥ä½ï¼éè¿CAS宿坹Stateå¼çä¿®æ¹ã #### 2.1.1 AQSæ°æ®ç»æ å æ¥çä¸AQSä¸æåºæ¬çæ°æ®ç»æââNodeï¼Nodeå³ä¸ºä¸é¢CLHåä½éåä¸çèç¹ã  è§£éä¸ä¸å ä¸ªæ¹æ³å屿§å¼çå«ä¹ï¼ | æ¹æ³å屿§å¼ | å«ä¹ | | :----------- | :----------------------------------------------------------- | | waitStatus | å½åèç¹å¨éåä¸çç¶æ | | thread | 表示å¤äºè¯¥èç¹ççº¿ç¨ | | prev | å驱æé | | predecessor | è¿åå驱èç¹ï¼æ²¡æçè¯æåºnpe | | nextWaiter | æåä¸ä¸ä¸ªå¤äºCONDITIONç¶æçèç¹ï¼ç±äºæ¬ç¯æç« ä¸è®²è¿°Condition Queueéåï¼è¿ä¸ªæéä¸å¤ä»ç»ï¼ | | next | åç»§æé | 线ç¨ä¸¤ç§éçæ¨¡å¼ï¼ | æ¨¡å¼ | å«ä¹ | | :-------- | :----------------------------- | | SHARED | 表示线ç¨ä»¥å ±äº«ç模å¼çå¾ é | | EXCLUSIVE | è¡¨ç¤ºçº¿ç¨æ£å¨ä»¥ç¬å çæ¹å¼çå¾ é | waitStatusæä¸é¢å 个æä¸¾å¼ï¼ | æä¸¾ | å«ä¹ | | :-------- | :--------------------------------------------- | | 0 | å½ä¸ä¸ªNode被åå§åçæ¶åçé»è®¤å¼ | | CANCELLED | 为1ï¼è¡¨ç¤ºçº¿ç¨è·åéç请æ±å·²ç»åæ¶äº | | CONDITION | 为-2ï¼è¡¨ç¤ºèç¹å¨çå¾ éåä¸ï¼èç¹çº¿ç¨çå¾ å¤é | | PROPAGATE | 为-3ï¼å½å线ç¨å¤å¨SHAREDæ åµä¸ï¼è¯¥å段æä¼ä½¿ç¨ | | SIGNAL | 为-1ï¼è¡¨ç¤ºçº¿ç¨å·²ç»åå¤å¥½äºï¼å°±çèµæºéæ¾äº | #### 2.1.2 åæ¥ç¶æState å¨äºè§£æ°æ®ç»æåï¼æ¥ä¸æ¥äºè§£ä¸ä¸AQSçåæ¥ç¶æââStateãAQSä¸ç»´æ¤äºä¸ä¸ªå为stateçåæ®µï¼æä¸ºåæ¥ç¶æï¼æ¯ç±Volatile修饰çï¼ç¨äºå±ç¤ºå½å临çèµæºçè·éæ åµã ```java // java.util.concurrent.locks.AbstractQueuedSynchronizer private volatile int state; ``` ä¸é¢æä¾äºå 个访é®è¿ä¸ªåæ®µçæ¹æ³ï¼ | æ¹æ³å | æè¿° | | :----------------------------------------------------------- | :------------------- | | protected final int getState() | è·åStateçå¼ | | protected final void setState(int newState) | 设置Stateçå¼ | | protected final boolean compareAndSetState(int expect, int update) | 使ç¨CASæ¹å¼æ´æ°State | è¿å ä¸ªæ¹æ³é½æ¯Final修饰çï¼è¯´æåç±»ä¸æ æ³éåå®ä»¬ãæä»¬å¯ä»¥éè¿ä¿®æ¹Stateåæ®µè¡¨ç¤ºçåæ¥ç¶ææ¥å®ç°å¤çº¿ç¨çç¬å 模å¼åå ±äº«æ¨¡å¼ï¼å éè¿ç¨ï¼ã   å¯¹äºæä»¬èªå®ä¹çåæ¥å·¥å ·ï¼éè¦èªå®ä¹è·ååæ¥ç¶æåéæ¾ç¶æçæ¹å¼ï¼ä¹å°±æ¯AQSæ¶æå¾ä¸ç第ä¸å±ï¼APIå±ã ## 2.2 AQSéè¦æ¹æ³ä¸ReentrantLockçå ³è 仿¶æå¾ä¸å¯ä»¥å¾ç¥ï¼AQSæä¾äºå¤§éç¨äºèªå®ä¹åæ¥å¨å®ç°çProtectedæ¹æ³ãèªå®ä¹åæ¥å¨å®ç°çç¸å ³æ¹æ³ä¹åªæ¯ä¸ºäºéè¿ä¿®æ¹Stateåæ®µæ¥å®ç°å¤çº¿ç¨çç¬å æ¨¡å¼æè å ±äº«æ¨¡å¼ãèªå®ä¹åæ¥å¨éè¦å®ç°ä»¥ä¸æ¹æ³ï¼ReentrantLockéè¦å®ç°çæ¹æ³å¦ä¸ï¼å¹¶ä¸æ¯å ¨é¨ï¼ï¼ | æ¹æ³å | æè¿° | | :------------------------------------------ | :----------------------------------------------------------- | | protected boolean isHeldExclusively() | è¯¥çº¿ç¨æ¯å¦æ£å¨ç¬å èµæºãåªæç¨å°Conditionæéè¦å»å®ç°å®ã | | protected boolean tryAcquire(int arg) | ç¬å æ¹å¼ãarg为è·åéçæ¬¡æ°ï¼å°è¯è·åèµæºï¼æååè¿åTrueï¼å¤±è´¥åè¿åFalseã | | protected boolean tryRelease(int arg) | ç¬å æ¹å¼ãargä¸ºéæ¾éçæ¬¡æ°ï¼å°è¯éæ¾èµæºï¼æååè¿åTrueï¼å¤±è´¥åè¿åFalseã | | protected int tryAcquireShared(int arg) | å ±äº«æ¹å¼ãarg为è·åéçæ¬¡æ°ï¼å°è¯è·åèµæºãè´æ°è¡¨ç¤ºå¤±è´¥ï¼0表示æåï¼ä½æ²¡æå©ä½å¯ç¨èµæºï¼æ£æ°è¡¨ç¤ºæåï¼ä¸æå©ä½èµæºã | | protected boolean tryReleaseShared(int arg) | å ±äº«æ¹å¼ãargä¸ºéæ¾éçæ¬¡æ°ï¼å°è¯éæ¾èµæºï¼å¦æéæ¾åå 许å¤éåç»çå¾ ç»ç¹è¿åTrueï¼å¦åè¿åFalseã | ä¸è¬æ¥è¯´ï¼èªå®ä¹åæ¥å¨è¦ä¹æ¯ç¬å æ¹å¼ï¼è¦ä¹æ¯å ±äº«æ¹å¼ï¼å®ä»¬ä¹åªéå®ç°tryAcquire-tryReleaseãtryAcquireShared-tryReleaseSharedä¸çä¸ç§å³å¯ãAQS乿¯æèªå®ä¹åæ¥å¨åæ¶å®ç°ç¬å åå ±äº«ä¸¤ç§æ¹å¼ï¼å¦ReentrantReadWriteLockãReentrantLockæ¯ç¬å éï¼æä»¥å®ç°äºtryAcquire-tryReleaseã 以éå ¬å¹³é为ä¾ï¼è¿é主è¦éè¿°ä¸ä¸éå ¬å¹³éä¸AQSä¹é´æ¹æ³çå ³èä¹å¤ï¼å ·ä½æ¯ä¸å¤æ ¸å¿æ¹æ³çä½ç¨ä¼å¨æç« åé¢è¯¦ç»è¿è¡éè¿°ã  为äºå¸®å©å¤§å®¶çè§£ReentrantLockåAQSä¹é´æ¹æ³ç交äºè¿ç¨ï¼ä»¥éå ¬å¹³é为ä¾ï¼æä»¬å°å éåè§£éçäº¤äºæµç¨åç¬æåºæ¥å¼ºè°ä¸ä¸ï¼ä»¥ä¾¿äºå¯¹åç»å 容ççè§£ã  å éï¼ - éè¿ReentrantLockçå éæ¹æ³Lockè¿è¡å éæä½ã - ä¼è°ç¨å°å é¨ç±»SyncçLockæ¹æ³ï¼ç±äºSync#lockæ¯æ½è±¡æ¹æ³ï¼æ ¹æ®ReentrantLockåå§åéæ©çå ¬å¹³éåéå ¬å¹³éï¼æ§è¡ç¸å ³å é¨ç±»çLockæ¹æ³ï¼æ¬è´¨ä¸é½ä¼æ§è¡AQSçAcquireæ¹æ³ã - AQSçAcquireæ¹æ³ä¼æ§è¡tryAcquireæ¹æ³ï¼ä½æ¯ç±äºtryAcquireéè¦èªå®ä¹åæ¥å¨å®ç°ï¼å æ¤æ§è¡äºReentrantLockä¸çtryAcquireæ¹æ³ï¼ç±äºReentrantLockæ¯éè¿å ¬å¹³éåéå ¬å¹³éå é¨ç±»å®ç°çtryAcquireæ¹æ³ï¼å æ¤ä¼æ ¹æ®éç±»åä¸åï¼æ§è¡ä¸åçtryAcquireã - tryAcquireæ¯è·åéé»è¾ï¼è·å失败åï¼ä¼æ§è¡æ¡æ¶AQSçåç»é»è¾ï¼è·ReentrantLockèªå®ä¹åæ¥å¨æ å ³ã è§£éï¼ - éè¿ReentrantLockçè§£éæ¹æ³Unlockè¿è¡è§£éã - Unlockä¼è°ç¨å é¨ç±»SyncçReleaseæ¹æ³ï¼è¯¥æ¹æ³ç»§æ¿äºAQSã - Releaseä¸ä¼è°ç¨tryReleaseæ¹æ³ï¼tryReleaseéè¦èªå®ä¹åæ¥å¨å®ç°ï¼tryReleaseåªå¨ReentrantLockä¸çSyncå®ç°ï¼å æ¤å¯ä»¥çåºï¼éæ¾éçè¿ç¨ï¼å¹¶ä¸åºåæ¯å¦ä¸ºå ¬å¹³éã - éæ¾æååï¼ææå¤çç±AQSæ¡æ¶å®æï¼ä¸èªå®ä¹åæ¥å¨æ å ³ã éè¿ä¸é¢çæè¿°ï¼å¤§æ¦å¯ä»¥æ»ç»åºReentrantLockå éè§£éæ¶API屿 ¸å¿æ¹æ³çæ å°å ³ç³»ã  ## 2.3 éè¿ReentrantLockçè§£AQS ReentrantLockä¸å ¬å¹³éåéå ¬å¹³éå¨åºå±æ¯ç¸åçï¼è¿é以éå ¬å¹³é为ä¾è¿è¡åæã å¨éå ¬å¹³éä¸ï¼æä¸æ®µè¿æ ·ç代ç ï¼ ```java // java.util.concurrent.locks.ReentrantLock static final class NonfairSync extends Sync { ... final void lock() { if (compareAndSetState(0, 1)) setExclusiveOwnerThread(Thread.currentThread()); else acquire(1); } ... } ``` çä¸ä¸è¿ä¸ªAcquireæ¯æä¹åçï¼ ```java // java.util.concurrent.locks.AbstractQueuedSynchronizer public final void acquire(int arg) { if (!tryAcquire(arg) && acquireQueued(addWaiter(Node.EXCLUSIVE), arg)) selfInterrupt(); } ``` åçä¸ä¸tryAcquireæ¹æ³ï¼ ```java // java.util.concurrent.locks.AbstractQueuedSynchronizer protected boolean tryAcquire(int arg) { throw new UnsupportedOperationException(); } ``` å¯ä»¥çåºï¼è¿éåªæ¯AQSçç®åå®ç°ï¼å ·ä½è·åéçå®ç°æ¹æ³æ¯ç±åèªçå ¬å¹³éåéå ¬å¹³éåç¬å®ç°çï¼ä»¥ReentrantLock为ä¾ï¼ãå¦æè¯¥æ¹æ³è¿åäºTrueï¼å说æå½å线ç¨è·åéæåï¼å°±ä¸ç¨å¾åæ§è¡äºï¼å¦æè·å失败ï¼å°±éè¦å å ¥å°çå¾ éåä¸ãä¸é¢ä¼è¯¦ç»è§£éçº¿ç¨æ¯ä½æ¶ä»¥åææ ·è¢«å å ¥è¿çå¾ éåä¸çã ### 2.3.1 线ç¨å å ¥çå¾ éå #### 2.3.1.1 å å ¥éåçæ¶æº å½æ§è¡Acquire(1)æ¶ï¼ä¼éè¿tryAcquireè·åéãå¨è¿ç§æ åµä¸ï¼å¦æè·åé失败ï¼å°±ä¼è°ç¨addWaiterå å ¥å°çå¾ éåä¸å»ã #### 2.3.1.2 å¦ä½å å ¥éå è·åé失败åï¼ä¼æ§è¡addWaiter(Node.EXCLUSIVE)å å ¥çå¾ éåï¼å ·ä½å®ç°æ¹æ³å¦ä¸ï¼ ```java // java.util.concurrent.locks.AbstractQueuedSynchronizer private Node addWaiter(Node mode) { Node node = new Node(Thread.currentThread(), mode); // Try the fast path of enq; backup to full enq on failure Node pred = tail; if (pred != null) { node.prev = pred; if (compareAndSetTail(pred, node)) { pred.next = node; return node; } } enq(node); return node; } private final boolean compareAndSetTail(Node expect, Node update) { return unsafe.compareAndSwapObject(this, tailOffset, expect, update); } ``` 主è¦çæµç¨å¦ä¸ï¼ - éè¿å½åç线ç¨å鿍¡å¼æ°å»ºä¸ä¸ªèç¹ã - Predæéæåå°¾èç¹Tailã - å°Newä¸NodeçPrevæéæåPredã - éè¿compareAndSetTailæ¹æ³ï¼å®æå°¾èç¹ç设置ãè¿ä¸ªæ¹æ³ä¸»è¦æ¯å¯¹tailOffsetåExpectè¿è¡æ¯è¾ï¼å¦ætailOffsetçNodeåExpectçNodeå°åæ¯ç¸åçï¼é£ä¹è®¾ç½®Tailçå¼ä¸ºUpdateçå¼ã ```java // java.util.concurrent.locks.AbstractQueuedSynchronizer static { try { stateOffset = unsafe.objectFieldOffset(AbstractQueuedSynchronizer.class.getDeclaredField("state")); headOffset = unsafe.objectFieldOffset(AbstractQueuedSynchronizer.class.getDeclaredField("head")); tailOffset = unsafe.objectFieldOffset(AbstractQueuedSynchronizer.class.getDeclaredField("tail")); waitStatusOffset = unsafe.objectFieldOffset(Node.class.getDeclaredField("waitStatus")); nextOffset = unsafe.objectFieldOffset(Node.class.getDeclaredField("next")); } catch (Exception ex) { throw new Error(ex); } } ``` ä»AQSçéæä»£ç åå¯ä»¥çåºï¼é½æ¯è·åä¸ä¸ªå¯¹è±¡ç屿§ç¸å¯¹äºè¯¥å¯¹è±¡å¨å åå½ä¸çåç§»éï¼è¿æ ·æä»¬å°±å¯ä»¥æ ¹æ®è¿ä¸ªåç§»éå¨å¯¹è±¡å åå½ä¸æ¾å°è¿ä¸ªå±æ§ãtailOffsetæçæ¯tail对åºçåç§»éï¼æä»¥è¿ä¸ªæ¶åä¼å°newåºæ¥çNode置为å½åéåçå°¾èç¹ãåæ¶ï¼ç±äºæ¯ååé¾è¡¨ï¼ä¹éè¦å°åä¸ä¸ªèç¹æåå°¾èç¹ã - 妿Predæéæ¯Nullï¼è¯´æçå¾ éå䏿²¡æå ç´ ï¼ï¼æè å½åPredæéåTailæåçä½ç½®ä¸åï¼è¯´æè¢«å«ç线ç¨å·²ç»ä¿®æ¹ï¼ï¼å°±éè¦çä¸ä¸Enqçæ¹æ³ã ```java // java.util.concurrent.locks.AbstractQueuedSynchronizer private Node enq(final Node node) { for (;;) { Node t = tail; if (t == null) { // Must initialize if (compareAndSetHead(new Node())) tail = head; } else { node.prev = t; if (compareAndSetTail(t, node)) { t.next = node; return t; } } } } ``` å¦ææ²¡æè¢«åå§åï¼éè¦è¿è¡åå§åä¸ä¸ªå¤´ç»ç¹åºæ¥ãä½è¯·æ³¨æï¼åå§åç头ç»ç¹å¹¶ä¸æ¯å½å线ç¨èç¹ï¼èæ¯è°ç¨äºæ åæé 彿°çèç¹ã妿ç»åäºåå§åæè å¹¶å导è´éå䏿å ç´ ï¼åä¸ä¹åçæ¹æ³ç¸åãå ¶å®ï¼addWaiterå°±æ¯ä¸ä¸ªå¨å端é¾è¡¨æ·»å å°¾èç¹çæä½ï¼éè¦æ³¨æçæ¯ï¼å端é¾è¡¨ç头ç»ç¹æ¯ä¸ä¸ªæ åæé 彿°ç头ç»ç¹ã æ»ç»ä¸ä¸ï¼çº¿ç¨è·åéçæ¶åï¼è¿ç¨å¤§ä½å¦ä¸ï¼ 1. 彿²¡æçº¿ç¨è·åå°éæ¶ï¼çº¿ç¨1è·åéæåã 2. 线ç¨2ç³è¯·éï¼ä½æ¯é被线ç¨1å æã  1. 妿åæçº¿ç¨è¦è·åéï¼ä¾æ¬¡å¨éåä¸å¾åæéå³å¯ã åå°ä¸è¾¹ç代ç ï¼hasQueuedPredecessorsæ¯å ¬å¹³éå 鿶夿çå¾ éå䏿¯å¦å卿æèç¹çæ¹æ³ã妿è¿åFalseï¼è¯´æå½å线ç¨å¯ä»¥äºåå ±äº«èµæºï¼å¦æè¿åTrueï¼è¯´æéåä¸å卿æèç¹ï¼å½å线ç¨å¿ é¡»å å ¥å°çå¾ éåä¸ã ```java // java.util.concurrent.locks.ReentrantLock public final boolean hasQueuedPredecessors() { // The correctness of this depends on head being initialized // before tail and on head.next being accurate if the current // thread is first in queue. Node t = tail; // Read fields in reverse initialization order Node h = head; Node s; return h != t && ((s = h.next) == null || s.thread != Thread.currentThread()); } ``` çå°è¿éï¼æä»¬çè§£ä¸ä¸h != t && ((s = h.next) == null || s.thread != Thread.currentThread());为ä»ä¹è¦å¤æç头ç»ç¹çä¸ä¸ä¸ªèç¹ï¼ç¬¬ä¸ä¸ªèç¹å¨åçæ°æ®æ¯ä»ä¹ï¼ > ååé¾è¡¨ä¸ï¼ç¬¬ä¸ä¸ªèç¹ä¸ºèèç¹ï¼å ¶å®å¹¶ä¸åå¨ä»»ä½ä¿¡æ¯ï¼åªæ¯å ä½ãçæ£ç第ä¸ä¸ªææ°æ®çèç¹ï¼æ¯å¨ç¬¬äºä¸ªèç¹å¼å§çãå½h != tæ¶ï¼ 妿(s = h.next) == nullï¼çå¾ éåæ£å¨æçº¿ç¨è¿è¡åå§åï¼ä½åªæ¯è¿è¡å°äºTailæåHeadï¼æ²¡æå°HeadæåTailï¼æ¤æ¶éå䏿å ç´ ï¼éè¦è¿åTrueï¼è¿åå ·ä½è§ä¸è¾¹ä»£ç åæï¼ã 妿(s = h.next) != nullï¼è¯´ææ¤æ¶éåä¸è³å°æä¸ä¸ªææèç¹ãå¦ææ¤æ¶s.thread == Thread.currentThread()ï¼è¯´æçå¾ éåç第ä¸ä¸ªææèç¹ä¸ç线ç¨ä¸å½å线ç¨ç¸åï¼é£ä¹å½åçº¿ç¨æ¯å¯ä»¥è·åèµæºçï¼å¦æs.thread != Thread.currentThread()ï¼è¯´æçå¾ éåç第ä¸ä¸ªææèç¹çº¿ç¨ä¸å½å线ç¨ä¸åï¼å½å线ç¨å¿ é¡»å å ¥è¿çå¾ éåã ```java // java.util.concurrent.locks.AbstractQueuedSynchronizer#enq if (t == null) { // Must initialize if (compareAndSetHead(new Node())) tail = head; } else { node.prev = t; if (compareAndSetTail(t, node)) { t.next = node; return t; } } ``` èç¹å ¥é䏿¯ååæä½ï¼æä»¥ä¼åºç°çæçhead != tailï¼æ¤æ¶Tailæåæåä¸ä¸ªèç¹ï¼èä¸TailæåHeadã妿Head没ææåTailï¼å¯è§5ã6ã7è¡ï¼ï¼è¿ç§æ åµä¸ä¹éè¦å°ç¸å ³çº¿ç¨å å ¥éåä¸ãæä»¥è¿åä»£ç æ¯ä¸ºäºè§£å³æç«¯æ åµä¸çå¹¶åé®é¢ã #### 2.3.1.3 çå¾ éåä¸çº¿ç¨åºéåæ¶æº åå°æåçæºç ï¼ ```java // java.util.concurrent.locks.AbstractQueuedSynchronizer public final void acquire(int arg) { if (!tryAcquire(arg) && acquireQueued(addWaiter(Node.EXCLUSIVE), arg)) selfInterrupt(); } ``` ä¸æè§£éäºaddWaiteræ¹æ³ï¼è¿ä¸ªæ¹æ³å ¶å®å°±æ¯æå¯¹åºç线ç¨ä»¥Nodeçæ°æ®ç»æå½¢å¼å å ¥å°å端éåéï¼è¿åçæ¯ä¸ä¸ªå å«è¯¥çº¿ç¨çNodeãèè¿ä¸ªNodeä¼ä½ä¸ºåæ°ï¼è¿å ¥å°acquireQueuedæ¹æ³ä¸ãacquireQueuedæ¹æ³å¯ä»¥å¯¹æéä¸ç线ç¨è¿è¡âè·éâæä½ã æ»çæ¥è¯´ï¼ä¸ä¸ªçº¿ç¨è·åé失败äºï¼è¢«æ¾å ¥çå¾ éåï¼acquireQueued伿æ¾å ¥éåä¸ç线ç¨ä¸æå»è·åéï¼ç´å°è·åæåæè ä¸åéè¦è·åï¼ä¸æï¼ã ä¸é¢æä»¬ä»â使¶åºéåï¼âåâå¦ä½åºéåï¼â两个æ¹åæ¥åæä¸ä¸acquireQueuedæºç ï¼ ```java // java.util.concurrent.locks.AbstractQueuedSynchronizer final boolean acquireQueued(final Node node, int arg) { // æ è®°æ¯å¦æåæ¿å°èµæº boolean failed = true; try { // æ è®°çå¾ è¿ç¨ä¸æ¯å¦ä¸æè¿ boolean interrupted = false; // å¼å§èªæï¼è¦ä¹è·åéï¼è¦ä¹ä¸æ for (;;) { // è·åå½åèç¹çå驱èç¹ final Node p = node.predecessor(); // 妿pæ¯å¤´ç»ç¹ï¼è¯´æå½åèç¹å¨ç宿°æ®éåçé¦é¨ï¼å°±å°è¯è·åéï¼å«å¿äºå¤´ç»ç¹æ¯èèç¹ï¼ if (p == head && tryAcquire(arg)) { // è·åéæåï¼å¤´æéç§»å¨å°å½ånode setHead(node); p.next = null; // help GC failed = false; return interrupted; } // 说æp为头èç¹ä¸å½å没æè·åå°éï¼å¯è½æ¯éå ¬å¹³é被æ¢å äºï¼æè æ¯pä¸ä¸ºå¤´ç»ç¹ï¼è¿ä¸ªæ¶åå°±è¦å¤æå½ånodeæ¯å¦è¦è¢«é»å¡ï¼è¢«é»å¡æ¡ä»¶ï¼å驱èç¹çwaitStatus为-1ï¼ï¼é²æ¢æ éå¾ªç¯æµªè´¹èµæºãå ·ä½ä¸¤ä¸ªæ¹æ³ä¸é¢ç»ç»åæ if (shouldParkAfterFailedAcquire(p, node) && parkAndCheckInterrupt()) interrupted = true; } } finally { if (failed) cancelAcquire(node); } } ``` 注ï¼setHeadæ¹æ³æ¯æå½åèç¹ç½®ä¸ºèèç¹ï¼ä½å¹¶æ²¡æä¿®æ¹waitStatusï¼å ä¸ºå®æ¯ä¸ç´éè¦ç¨çæ°æ®ã ```java // java.util.concurrent.locks.AbstractQueuedSynchronizer private void setHead(Node node) { head = node; node.thread = null; node.prev = null; } // java.util.concurrent.locks.AbstractQueuedSynchronizer // é å驱èç¹å¤æå½åçº¿ç¨æ¯å¦åºè¯¥è¢«é»å¡ private static boolean shouldParkAfterFailedAcquire(Node pred, Node node) { // è·å头ç»ç¹çèç¹ç¶æ int ws = pred.waitStatus; // 说æå¤´ç»ç¹å¤äºå¤éç¶æ if (ws == Node.SIGNAL) return true; // éè¿æä¸¾å¼æä»¬ç¥éwaitStatus>0æ¯åæ¶ç¶æ if (ws > 0) { do { // 循ç¯å忥æ¾åæ¶èç¹ï¼æåæ¶èç¹ä»éåä¸åé¤ node.prev = pred = pred.prev; } while (pred.waitStatus > 0); pred.next = node; } else { // 设置åä»»èç¹çå¾ ç¶æä¸ºSIGNAL compareAndSetWaitStatus(pred, ws, Node.SIGNAL); } return false; } ``` parkAndCheckInterrupt主è¦ç¨äºæèµ·å½å线ç¨ï¼é»å¡è°ç¨æ ï¼è¿åå½å线ç¨çä¸æç¶æã ```java // java.util.concurrent.locks.AbstractQueuedSynchronizer private final boolean parkAndCheckInterrupt() { LockSupport.park(this); return Thread.interrupted(); } ``` ä¸è¿°æ¹æ³çæµç¨å¾å¦ä¸ï¼  ä»ä¸å¾å¯ä»¥çåºï¼è·³åºå½å循ç¯çæ¡ä»¶æ¯å½âåç½®èç¹æ¯å¤´ç»ç¹ï¼ä¸å½å线ç¨è·åéæåâã为äºé²æ¢å æ»å¾ªç¯å¯¼è´CPUèµæºè¢«æµªè´¹ï¼æä»¬ä¼å¤æåç½®èç¹çç¶ææ¥å³å®æ¯å¦è¦å°å½åçº¿ç¨æèµ·ï¼å ·ä½æèµ·æµç¨ç¨æµç¨å¾è¡¨ç¤ºå¦ä¸ï¼shouldParkAfterFailedAcquireæµç¨ï¼ï¼  ä»éåä¸éæ¾èç¹ççèææ¶äºï¼é£ä¹åææ°é®é¢äºï¼ - shouldParkAfterFailedAcquireä¸åæ¶èç¹æ¯æä¹çæçå¢ï¼ä»ä¹æ¶å伿ä¸ä¸ªèç¹çwaitStatus设置为-1ï¼ - æ¯å¨ä»ä¹æ¶é´éæ¾èç¹éç¥å°è¢«æèµ·ç线ç¨å¢ï¼ ### 2.3.2 CANCELLEDç¶æèç¹çæ acquireQueuedæ¹æ³ä¸çFinally代ç ï¼ ```java // java.util.concurrent.locks.AbstractQueuedSynchronizer final boolean acquireQueued(final Node node, int arg) { boolean failed = true; try { ... for (;;) { final Node p = node.predecessor(); if (p == head && tryAcquire(arg)) { ... failed = false; ... } ... } finally { if (failed) cancelAcquire(node); } } ``` éè¿cancelAcquireæ¹æ³ï¼å°Nodeçç¶ææ 记为CANCELLEDãæ¥ä¸æ¥ï¼æä»¬éè¡æ¥åæè¿ä¸ªæ¹æ³çåçï¼ ```java // java.util.concurrent.locks.AbstractQueuedSynchronizer private void cancelAcquire(Node node) { // å°æ æèç¹è¿æ»¤ if (node == null) return; // 设置该èç¹ä¸å ³èä»»ä½çº¿ç¨ï¼ä¹å°±æ¯èèç¹ node.thread = null; Node pred = node.prev; // éè¿å驱èç¹ï¼è·³è¿åæ¶ç¶æçnode while (pred.waitStatus > 0) node.prev = pred = pred.prev; // è·åè¿æ»¤åçå驱èç¹çåç»§èç¹ Node predNext = pred.next; // æå½ånodeçç¶æè®¾ç½®ä¸ºCANCELLED node.waitStatus = Node.CANCELLED; // 妿å½åèç¹æ¯å°¾èç¹ï¼å°ä»åå¾åç第ä¸ä¸ªéåæ¶ç¶æçèç¹è®¾ç½®ä¸ºå°¾èç¹ // æ´æ°å¤±è´¥çè¯ï¼åè¿å ¥elseï¼å¦ææ´æ°æåï¼å°tailçåç»§èç¹è®¾ç½®ä¸ºnull if (node == tail && compareAndSetTail(node, pred)) { compareAndSetNext(pred, predNext, null); } else { int ws; // 妿å½åèç¹ä¸æ¯headçåç»§èç¹ï¼1:夿å½åèç¹å驱èç¹çæ¯å¦ä¸ºSIGNALï¼2:妿䏿¯ï¼åæå驱èç¹è®¾ç½®ä¸ºSINGALçæ¯å¦æå // 妿1å2䏿ä¸ä¸ªä¸ºtrueï¼å夿å½åèç¹ççº¿ç¨æ¯å¦ä¸ºnull // 妿ä¸è¿°æ¡ä»¶é½æ»¡è¶³ï¼æå½åèç¹çå驱èç¹çåç»§æéæåå½åèç¹çåç»§èç¹ if (pred != head && ((ws = pred.waitStatus) == Node.SIGNAL || (ws <= 0 && compareAndSetWaitStatus(pred, ws, Node.SIGNAL))) && pred.thread != null) { Node next = node.next; if (next != null && next.waitStatus <= 0) compareAndSetNext(pred, predNext, next); } else { // 妿å½åèç¹æ¯headçåç»§èç¹ï¼æè ä¸è¿°æ¡ä»¶ä¸æ»¡è¶³ï¼é£å°±å¤éå½åèç¹çåç»§èç¹ unparkSuccessor(node); } node.next = node; // help GC } } ``` å½åçæµç¨ï¼ - è·åå½åèç¹çå驱èç¹ï¼å¦æå驱èç¹çç¶ææ¯CANCELLEDï¼é£å°±ä¸ç´å¾åéåï¼æ¾å°ç¬¬ä¸ä¸ªwaitStatus <= 0çèç¹ï¼å°æ¾å°çPredèç¹åå½åNodeå ³èï¼å°å½åNode设置为CANCELLEDã - æ ¹æ®å½åèç¹çä½ç½®ï¼èè以ä¸ä¸ç§æ åµï¼ (1) å½åèç¹æ¯å°¾èç¹ã (2) å½åèç¹æ¯Headçåç»§èç¹ã (3) å½åèç¹ä¸æ¯Headçåç»§èç¹ï¼ä¹ä¸æ¯å°¾èç¹ã æ ¹æ®ä¸è¿°ç¬¬äºæ¡ï¼æä»¬æ¥åææ¯ä¸ç§æ åµçæµç¨ã å½åèç¹æ¯å°¾èç¹ã  å½åèç¹æ¯Headçåç»§èç¹ã  å½åèç¹ä¸æ¯Headçåç»§èç¹ï¼ä¹ä¸æ¯å°¾èç¹ã  éè¿ä¸é¢çæµç¨ï¼æä»¬å¯¹äºCANCELLEDèç¹ç¶æç产çåååå·²ç»æäºå¤§è´çäºè§£ï¼ä½æ¯ä¸ºä»ä¹ææçåå齿¯å¯¹Nextæéè¿è¡äºæä½ï¼è没æå¯¹Prevæéè¿è¡æä½å¢ï¼ä»ä¹æ åµä¸ä¼å¯¹Prevæéè¿è¡æä½ï¼ > æ§è¡cancelAcquireçæ¶åï¼å½åèç¹çåç½®èç¹å¯è½å·²ç»ä»éåä¸åºå»äºï¼å·²ç»æ§è¡è¿Try代ç åä¸çshouldParkAfterFailedAcquireæ¹æ³äºï¼ï¼å¦ææ¤æ¶ä¿®æ¹Prevæéï¼æå¯è½ä¼å¯¼è´Prevæåå¦ä¸ä¸ªå·²ç»ç§»é¤éåçNodeï¼å æ¤è¿åååPrevæéä¸å®å ¨ã shouldParkAfterFailedAcquireæ¹æ³ä¸ï¼ä¼æ§è¡ä¸é¢ç代ç ï¼å ¶å®å°±æ¯å¨å¤çPrevæéãshouldParkAfterFailedAcquireæ¯è·åéå¤±è´¥çæ åµä¸æä¼æ§è¡ï¼è¿å ¥è¯¥æ¹æ³åï¼è¯´æå ±äº«èµæºå·²è¢«è·åï¼å½åèç¹ä¹åçèç¹é½ä¸ä¼åºç°ååï¼å æ¤è¿ä¸ªæ¶ååæ´Prevæéæ¯è¾å®å ¨ã > > ```java > do { > node.prev = pred = pred.prev; > } while (pred.waitStatus > 0); > ``` ### 2.3.3 å¦ä½è§£é æä»¬å·²ç»åæäºå éè¿ç¨ä¸çåºæ¬æµç¨ï¼æ¥ä¸æ¥å对解éçåºæ¬æµç¨è¿è¡åæãç±äºReentrantLockå¨è§£éçæ¶åï¼å¹¶ä¸åºåå ¬å¹³éåéå ¬å¹³éï¼æä»¥æä»¬ç´æ¥çè§£éçæºç ï¼ ```java // java.util.concurrent.locks.ReentrantLock public void unlock() { sync.release(1); } ``` å¯ä»¥çå°ï¼æ¬è´¨éæ¾éçå°æ¹ï¼æ¯éè¿æ¡æ¶æ¥å®æçã ```java // java.util.concurrent.locks.AbstractQueuedSynchronizer public final boolean release(int arg) { if (tryRelease(arg)) { Node h = head; if (h != null && h.waitStatus != 0) unparkSuccessor(h); return true; } return false; } ``` å¨ReentrantLockéé¢çå ¬å¹³éåéå ¬å¹³éçç¶ç±»Syncå®ä¹äºå¯éå ¥éçéæ¾éæºå¶ã ```java // java.util.concurrent.locks.ReentrantLock.Sync // æ¹æ³è¿åå½å鿝䏿¯æ²¡æè¢«çº¿ç¨ææ protected final boolean tryRelease(int releases) { // åå°å¯éå ¥æ¬¡æ° int c = getState() - releases; // å½å线ç¨ä¸æ¯ææéç线ç¨ï¼æåºå¼å¸¸ if (Thread.currentThread() != getExclusiveOwnerThread()) throw new IllegalMonitorStateException(); boolean free = false; // 妿ææçº¿ç¨å ¨é¨éæ¾ï¼å°å½åç¬å éææçº¿ç¨è®¾ç½®ä¸ºnullï¼å¹¶æ´æ°state if (c == 0) { free = true; setExclusiveOwnerThread(null); } setState(c); return free; } ``` æä»¬æ¥è§£éä¸è¿°æºç ï¼ ```java // java.util.concurrent.locks.AbstractQueuedSynchronizer public final boolean release(int arg) { // ä¸è¾¹èªå®ä¹çtryRelease妿è¿åtrueï¼è¯´æè¯¥é没æè¢«ä»»ä½çº¿ç¨ææ if (tryRelease(arg)) { // è·å头ç»ç¹ Node h = head; // 头ç»ç¹ä¸ä¸ºç©ºå¹¶ä¸å¤´ç»ç¹çwaitStatus䏿¯åå§åèç¹æ åµï¼è§£é¤çº¿ç¨æèµ·ç¶æ if (h != null && h.waitStatus != 0) unparkSuccessor(h); return true; } return false; } ``` è¿éç夿æ¡ä»¶ä¸ºä»ä¹æ¯h != null && h.waitStatus != 0ï¼ > h == null Headè¿æ²¡åå§åãåå§æ åµä¸ï¼head == nullï¼ç¬¬ä¸ä¸ªèç¹å ¥éï¼Headä¼è¢«åå§åä¸ä¸ªèæèç¹ãæä»¥è¯´ï¼è¿éå¦æè¿æ²¡æ¥å¾åå ¥éï¼å°±ä¼åºç°head == null çæ åµã > > h != null && waitStatus == 0 表æåç»§èç¹å¯¹åºç线ç¨ä»å¨è¿è¡ä¸ï¼ä¸éè¦å¤éã > > h != null && waitStatus < 0 表æåç»§èç¹å¯è½è¢«é»å¡äºï¼éè¦å¤éã åçä¸ä¸unparkSuccessoræ¹æ³ï¼ ```java // java.util.concurrent.locks.AbstractQueuedSynchronizer private void unparkSuccessor(Node node) { // è·å头ç»ç¹waitStatus int ws = node.waitStatus; if (ws < 0) compareAndSetWaitStatus(node, ws, 0); // è·åå½åèç¹çä¸ä¸ä¸ªèç¹ Node s = node.next; // 妿ä¸ä¸ªèç¹æ¯nullæè ä¸ä¸ªèç¹è¢«cancelledï¼å°±æ¾å°éåæå¼å§çécancelledçèç¹ if (s == null || s.waitStatus > 0) { s = null; // å°±ä»å°¾é¨èç¹å¼å§æ¾ï¼å°éé¦ï¼æ¾å°éå第ä¸ä¸ªwaitStatus<0çèç¹ã for (Node t = tail; t != null && t != node; t = t.prev) if (t.waitStatus <= 0) s = t; } // 妿å½åèç¹çä¸ä¸ªèç¹ä¸ä¸ºç©ºï¼èä¸ç¶æ<=0ï¼å°±æå½åèç¹unpark if (s != null) LockSupport.unpark(s.thread); } ``` 为ä»ä¹è¦ä»åå¾åæ¾ç¬¬ä¸ä¸ªéCancelledçèç¹å¢ï¼åå å¦ä¸ã ä¹åçaddWaiteræ¹æ³ï¼ ```java // java.util.concurrent.locks.AbstractQueuedSynchronizer private Node addWaiter(Node mode) { Node node = new Node(Thread.currentThread(), mode); // Try the fast path of enq; backup to full enq on failure Node pred = tail; if (pred != null) { node.prev = pred; if (compareAndSetTail(pred, node)) { pred.next = node; return node; } } enq(node); return node; } ``` æä»¬ä»è¿éå¯ä»¥çå°ï¼èç¹å ¥é并䏿¯ååæä½ï¼ä¹å°±æ¯è¯´ï¼node.prev = pred; compareAndSetTail(pred, node) è¿ä¸¤ä¸ªå°æ¹å¯ä»¥çä½Tailå ¥éçååæä½ï¼ä½æ¯æ¤æ¶pred.next = node;è¿æ²¡æ§è¡ï¼å¦æè¿ä¸ªæ¶åæ§è¡äºunparkSuccessoræ¹æ³ï¼å°±æ²¡åæ³ä»åå¾åæ¾äºï¼æä»¥éè¦ä»åå¾åæ¾ãè¿æä¸ç¹åå ï¼å¨äº§çCANCELLEDç¶æèç¹çæ¶åï¼å æå¼çæ¯Nextæéï¼Prevæéå¹¶æªæå¼ï¼å æ¤ä¹æ¯å¿ é¡»è¦ä»åå¾åéåæè½å¤éåå®å ¨é¨çNodeã ç»¼ä¸æè¿°ï¼å¦ææ¯ä»åå¾åæ¾ï¼ç±äºæç«¯æ åµä¸å ¥éçéååæä½åCANCELLEDèç¹äº§çè¿ç¨ä¸æå¼Nextæéçæä½ï¼å¯è½ä¼å¯¼è´æ æ³éåææçèç¹ãæä»¥ï¼å¤é对åºç线ç¨åï¼å¯¹åºç线ç¨å°±ä¼ç»§ç»å¾ä¸æ§è¡ãç»§ç»æ§è¡acquireQueuedæ¹æ³ä»¥åï¼ä¸æå¦ä½å¤çï¼ ### 2.3.4 䏿æ¢å¤åçæ§è¡æµç¨ å¤éåï¼ä¼æ§è¡return Thread.interrupted();ï¼è¿ä¸ªå½æ°è¿åçæ¯å½åæ§è¡çº¿ç¨çä¸æç¶æï¼å¹¶æ¸ é¤ã ```java // java.util.concurrent.locks.AbstractQueuedSynchronizer private final boolean parkAndCheckInterrupt() { LockSupport.park(this); return Thread.interrupted(); } ``` ååå°acquireQueued代ç ï¼å½parkAndCheckInterruptè¿åTrueæè Falseçæ¶åï¼interruptedçå¼ä¸åï¼ä½é½ä¼æ§è¡ä¸æ¬¡å¾ªç¯ã妿è¿ä¸ªæ¶åè·åéæåï¼å°±ä¼æå½åinterruptedè¿åã ```java // java.util.concurrent.locks.AbstractQueuedSynchronizer final boolean acquireQueued(final Node node, int arg) { boolean failed = true; try { boolean interrupted = false; for (;;) { final Node p = node.predecessor(); if (p == head && tryAcquire(arg)) { setHead(node); p.next = null; // help GC failed = false; return interrupted; } if (shouldParkAfterFailedAcquire(p, node) && parkAndCheckInterrupt()) interrupted = true; } } finally { if (failed) cancelAcquire(node); } } ``` 妿acquireQueued为Trueï¼å°±ä¼æ§è¡selfInterruptæ¹æ³ã ```java // java.util.concurrent.locks.AbstractQueuedSynchronizer static void selfInterrupt() { Thread.currentThread().interrupt(); } ``` è¯¥æ¹æ³å ¶å®æ¯ä¸ºäºä¸æçº¿ç¨ãä½ä¸ºä»ä¹è·åäºé以åè¿è¦ä¸æçº¿ç¨å¢ï¼è¿é¨åå±äºJavaæä¾çåä½å¼ä¸æç¥è¯å å®¹ï¼æå ´è¶£åå¦å¯ä»¥æ¥é ä¸ä¸ãè¿éç®åä»ç»ä¸ä¸ï¼ 1. å½ä¸æçº¿ç¨è¢«å¤éæ¶ï¼å¹¶ä¸ç¥é被å¤éçåå ï¼å¯è½æ¯å½å线ç¨å¨çå¾ ä¸è¢«ä¸æï¼ä¹å¯è½æ¯éæ¾äºé以å被å¤éãå æ¤æä»¬éè¿Thread.interrupted()æ¹æ³æ£æ¥ä¸ææ è®°ï¼è¯¥æ¹æ³è¿åäºå½å线ç¨çä¸æç¶æï¼å¹¶å°å½å线ç¨ç䏿æ è¯è®¾ç½®ä¸ºFalseï¼ï¼å¹¶è®°å½ä¸æ¥ï¼å¦æåç°è¯¥çº¿ç¨è¢«ä¸æè¿ï¼å°±å䏿䏿¬¡ã 2. 线ç¨å¨çå¾ èµæºçè¿ç¨ä¸è¢«å¤éï¼å¤éåè¿æ¯ä¼ä¸æå°å»å°è¯è·åéï¼ç´å°æ¢å°é为æ¢ãä¹å°±æ¯è¯´ï¼å¨æ´ä¸ªæµç¨ä¸ï¼å¹¶ä¸ååºä¸æï¼åªæ¯è®°å½ä¸æè®°å½ãæåæ¢å°éè¿åäºï¼é£ä¹å¦æè¢«ä¸æè¿çè¯ï¼å°±éè¦è¡¥å 䏿¬¡ä¸æã è¿éçå¤çæ¹å¼ä¸»è¦æ¯è¿ç¨çº¿ç¨æ± ä¸åºæ¬è¿ä½åå Worderä¸çrunWorkerï¼éè¿Thread.interrupted()è¿è¡é¢å¤ç夿å¤çï¼æå ´è¶£çåå¦å¯ä»¥çä¸ThreadPoolExecutoræºç ã ### 2.3.5 å°ç» æä»¬å¨1.3å°è䏿åºäºä¸äºé®é¢ï¼ç°å¨æ¥åçä¸ä¸ã > Qï¼æä¸ªçº¿ç¨è·åé失败çåç»æµç¨æ¯ä»ä¹å¢ï¼ > > Aï¼åå¨æç§æéçåæºå¶ï¼çº¿ç¨ç»§ç»çå¾ ï¼ä»ç¶ä¿çè·åéçå¯è½ï¼è·åéæµç¨ä»å¨ç»§ç»ã > > Qï¼æ¢ç¶è¯´å°äºæéçåæºå¶ï¼é£ä¹å°±ä¸å®ä¼ææç§éåå½¢æï¼è¿æ ·çé忝ä»ä¹æ°æ®ç»æå¢ï¼ > > Aï¼æ¯CLHåä½çFIFOå端éåã > > Qï¼å¤äºæéçåæºå¶ä¸ç线ç¨ï¼ä»ä¹æ¶åå¯ä»¥ææºä¼è·åéå¢ï¼ > > Aï¼å¯ä»¥è¯¦ç»çä¸2.3.1.3å°èã > > Qï¼å¦æå¤äºæéçåæºå¶ä¸ç线ç¨ä¸ç´æ æ³è·åéï¼éè¦ä¸ç´çå¾ ä¹ï¼è¿æ¯æå«ççç¥æ¥è§£å³è¿ä¸é®é¢ï¼ > > Aï¼çº¿ç¨æå¨èç¹çç¶æä¼åæåæ¶ç¶æï¼åæ¶ç¶æçèç¹ä¼ä»éåä¸éæ¾ï¼å ·ä½å¯è§2.3.2å°èã > > Qï¼Lock彿°éè¿Acquireæ¹æ³è¿è¡å éï¼ä½æ¯å ·ä½æ¯å¦ä½å éçå¢ï¼ > > Aï¼AQSçAcquireä¼è°ç¨tryAcquireæ¹æ³ï¼tryAcquireç±å个èªå®ä¹åæ¥å¨å®ç°ï¼éè¿tryAcquire宿å éè¿ç¨ã ## 3 AQSåºç¨ ### 3.1 ReentrantLockçå¯éå ¥åºç¨ ReentrantLockçå¯éå ¥æ§æ¯AQSå¾å¥½çåºç¨ä¹ä¸ï¼å¨äºè§£å®ä¸è¿°ç¥è¯ç¹ä»¥åï¼æä»¬å¾å®¹æå¾ç¥ReentrantLockå®ç°å¯éå ¥çæ¹æ³ãå¨ReentrantLockéé¢ï¼ä¸ç®¡æ¯å ¬å¹³éè¿æ¯éå ¬å¹³éï¼é½æä¸æ®µé»è¾ã å ¬å¹³éï¼ ```java // java.util.concurrent.locks.ReentrantLock.FairSync#tryAcquire if (c == 0) { if (!hasQueuedPredecessors() && compareAndSetState(0, acquires)) { setExclusiveOwnerThread(current); return true; } } else if (current == getExclusiveOwnerThread()) { int nextc = c + acquires; if (nextc < 0) throw new Error("Maximum lock count exceeded"); setState(nextc); return true; } ``` éå ¬å¹³éï¼ ```java // java.util.concurrent.locks.ReentrantLock.Sync#nonfairTryAcquire if (c == 0) { if (compareAndSetState(0, acquires)){ setExclusiveOwnerThread(current); return true; } } else if (current == getExclusiveOwnerThread()) { int nextc = c + acquires; if (nextc < 0) // overflow throw new Error("Maximum lock count exceeded"); setState(nextc); return true; } ``` ä»ä¸é¢è¿ä¸¤æ®µé½å¯ä»¥çå°ï¼æä¸ä¸ªåæ¥ç¶æStateæ¥æ§å¶æ´ä½å¯éå ¥çæ åµãStateæ¯Volatile修饰çï¼ç¨äºä¿è¯ä¸å®çå¯è§æ§åæåºæ§ã ```java // java.util.concurrent.locks.AbstractQueuedSynchronizer private volatile int state; ``` æ¥ä¸æ¥çStateè¿ä¸ªå段主è¦çè¿ç¨ï¼ 1. Stateåå§åçæ¶å为0ï¼è¡¨ç¤ºæ²¡æä»»ä½çº¿ç¨ææéã 2. å½æçº¿ç¨ææè¯¥éæ¶ï¼å¼å°±ä¼å¨åæ¥çåºç¡ä¸+1ï¼åä¸ä¸ªçº¿ç¨å¤æ¬¡è·å¾éæ¯ï¼å°±ä¼å¤æ¬¡+1ï¼è¿éå°±æ¯å¯éå ¥çæ¦å¿µã 3. è§£é乿¯å¯¹è¿ä¸ªå段-1ï¼ä¸ç´å°0ï¼æ¤çº¿ç¨å¯¹ééæ¾ã ### 3.2 JUCä¸çåºç¨åºæ¯ é¤äºä¸è¾¹ReentrantLockçå¯éå ¥æ§çåºç¨ï¼AQSä½ä¸ºå¹¶åç¼ç¨çæ¡æ¶ï¼ä¸ºå¾å¤å ¶ä»åæ¥å·¥å ·æä¾äºè¯å¥½çè§£å³æ¹æ¡ãä¸é¢ååºäºJUCä¸çå ç§åæ¥å·¥å ·ï¼å¤§ä½ä»ç»ä¸ä¸AQSçåºç¨åºæ¯ï¼ | åæ¥å·¥å · | åæ¥å·¥å ·ä¸AQSçå ³è | | :--------------------- | :----------------------------------------------------------- | | ReentrantLock | 使ç¨AQSä¿åéé夿æç次æ°ãå½ä¸ä¸ªçº¿ç¨è·åéæ¶ï¼ReentrantLockè®°å½å½åè·å¾éççº¿ç¨æ è¯ï¼ç¨äºæ£æµæ¯å¦éå¤è·åï¼ä»¥åé误线ç¨è¯å¾è§£éæä½æ¶å¼å¸¸æ åµçå¤çã | | Semaphore | 使ç¨AQSåæ¥ç¶ææ¥ä¿åä¿¡å·éçå½å计æ°ãtryReleaseä¼å¢å 计æ°ï¼acquireSharedä¼åå°è®¡æ°ã | | CountDownLatch | 使ç¨AQSåæ¥ç¶ææ¥è¡¨ç¤ºè®¡æ°ã计æ°ä¸º0æ¶ï¼ææçAcquireæä½ï¼CountDownLatchçawaitæ¹æ³ï¼æå¯ä»¥éè¿ã | | ReentrantReadWriteLock | 使ç¨AQSåæ¥ç¶æä¸ç16ä½ä¿ååéææçæ¬¡æ°ï¼å©ä¸ç16ä½ç¨äºä¿å读éçæææ¬¡æ°ã | | ThreadPoolExecutor | Workerå©ç¨AQSåæ¥ç¶æå®ç°å¯¹ç¬å 线ç¨åéç设置ï¼tryAcquireåtryReleaseï¼ã | ### 3.3 èªå®ä¹åæ¥å·¥å · äºè§£AQSåºæ¬åç以åï¼æç §ä¸é¢æè¯´çAQSç¥è¯ç¹ï¼èªå·±å®ç°ä¸ä¸ªåæ¥å·¥å ·ã ```java public class LeeLock { private static class Sync extends AbstractQueuedSynchronizer { @Override protected boolean tryAcquire (int arg) { return compareAndSetState(0, 1); } @Override protected boolean tryRelease (int arg) { setState(0); return true; } @Override protected boolean isHeldExclusively () { return getState() == 1; } } private Sync sync = new Sync(); public void lock () { sync.acquire(1); } public void unlock () { sync.release(1); } } ``` éè¿æä»¬èªå·±å®ä¹çLock宿ä¸å®ç忥åè½ã ```java public class LeeMain { static int count = 0; static LeeLock leeLock = new LeeLock(); public static void main (String[] args) throws InterruptedException { Runnable runnable = new Runnable() { @Override public void run () { try { leeLock.lock(); for (int i = 0; i < 10000; i++) { count++; } } catch (Exception e) { e.printStackTrace(); } finally { leeLock.unlock(); } } }; Thread thread1 = new Thread(runnable); Thread thread2 = new Thread(runnable); thread1.start(); thread2.start(); thread1.join(); thread2.join(); System.out.println(count); } } ``` ä¸è¿°ä»£ç æ¯æ¬¡è¿è¡ç»æé½ä¼æ¯20000ãéè¿ç®åçå è¡ä»£ç å°±è½å®ç°åæ¥åè½ï¼è¿å°±æ¯AQSç强大ä¹å¤ã ## æ»ç» æä»¬æ¥å¸¸å¼åä¸ä½¿ç¨å¹¶åçåºæ¯å¤ªå¤ï¼ä½æ¯å¯¹å¹¶åå é¨çåºæ¬æ¡æ¶åçäºè§£ç人å´ä¸å¤ãç±äºç¯å¹ åå ï¼æ¬æä» ä»ç»äºå¯éå ¥éReentrantLockçåçåAQSåçï¼å¸æè½å¤æä¸ºå¤§å®¶äºè§£AQSåReentrantLockç忥å¨çâæ²é¨ç âã ## åèèµæ - Lea D. The java. util. concurrent synchronizer framework[J]. Science of Computer Programming, 2005, 58(3): 293-309. - ãJavaå¹¶åç¼ç¨å®æã - [ä¸å¯ä¸è¯´çJavaâéâäº](https://tech.meituan.com/2018/11/15/java-lock.html)