AbstractQueuedSynchronizer::enqueue源码笔记

// 表示Node节点状态的常量
static final int WAITING   = 1;          // must be 1
static final int CANCELLED = 0x80000000; // must be negative
static final int COND      = 2;          // in a condition wait

// Node节点的结构,为了便于观看去除了方法代码
abstract static class Node {
    volatile Node prev;       // initially attached via casTail
    volatile Node next;       // visibly nonnull when signallable
    Thread waiter;            // visibly nonnull when enqueued
    volatile int status;      // written by owner, atomic bit ops by others

}

// Node节点入队操作,目前只有ConditionNode在用,其他节点目前在使用acquair方法
final void enqueue(Node node) {
    if (node != null) {
        // 死循环代表反复尝试直到插入成功
        for (;;) {
            Node t = tail;
            // 将node的前向指针指向当前的尾部节点
            node.setPrevRelaxed(t);        // avoid unnecessary fence
            // 如果发现头尾节点还没初始化,则此次循环先初始化头尾节点
            if (t == null)                 
                tryInitializeHead();
            // cas成功说明入队成功
            else if (casTail(t, node)) {
                // 完成入队的剩余工作,即修改前驱节点的next指针
                t.next = node;
                // 前驱节点已经处于CANCELLED状态,启动当前插入的节点所绑定的线程
                if (t.status < 0)          // wake up to clean link
                    LockSupport.unpark(node.waiter);
                break;
            }
        }
    }
}

 

posted @ 2021-03-30 11:55  榆木脑袋0v0  阅读(96)  评论(0)    收藏  举报