首页  

Synchronized 和 AQS 实现要点     所属分类 java 浏览量 143
锁机制两种基本形式 阻塞 和 自旋(CAS)
对象监视器上只能拥有一个同步队列和一个等待队列,并发包中的Lock可以拥有一个同步队列和多个等待队列


Synchronized 基于 Java对象头 和 Monitor机制 实现 对象在内存中包含三部分 对象头 实例数据 和 对齐填充 Class Metadata Address (类型指针) 通过该指针定位是哪个类的实例 Mark Word(标记字段) 对象运行时信息,包括哈希码,GC分代年龄,锁状态标志等 数组长度 (数组对象) 无锁 偏向锁 只需比较ThreadID 轻量级锁 自旋 指向栈中锁记录指针 重量级锁 依赖mutex(操作系统互斥) 指向 互斥量 指针 对象监视器 monitor 对象 同步队列 等待队列 _owner 当前持有锁的线程 _EntryList 所有阻塞等待锁的线程 多个线程竞争锁,先进入 EntryList 队列 ,竞争成功的线程标记为 Owner ,其他线程继续在此队列中阻塞等待 如果 Owner 线程执行完了,释放锁,Owner 置空,EntryList 中的线程再次竞争锁 如果 Owner 线程调用 wait() 方法,释放锁并进入 WaitSet 中等待被唤醒 Owner 置空,EntryList 中的线程再次竞争锁 _WaitSet 调用 wait() 方法并未被通知的线程 锁优化 锁消除 逃逸分析 锁粗化 自适应自旋 偏向锁 偏向于第一个持有它的线程 轻量级锁
AQS AbstractQueuedSynchronizer 常见的锁实现算法 TAS,TTAS ,CLH,MCS, AQS是CLH的一个变种,CLH适用于SMP数据结构,MCS适用于NUMA结构, CLH和MCS不同在于,CLH是轮询前驱节点的状态判断前驱节点是否释放锁, MCS是轮询自身节点状态来判断是否可以获得锁,前驱节点释放锁的时候更新后一节点的状态 Java中的大部分同步类(Lock、Semaphore、ReentrantLock等)都是基于AbstractQueuedSynchronizer(AQS)实现的。 AQS 是一种提供了原子式管理同步状态、阻塞和唤醒线程功能以及队列模型的简单框架 AQS 两个重要成员 state 表示锁状态,volatile 修饰 , CAS 操作 state变量 state 为0表示没有任何线程持有锁,线程持有该锁后将 state 加1,释放时减1 多次持有释放则多次加减 ,可重入 AQS维护两个队列 AQS类维护的CLH队列,用于锁机制的实现 AQS的内部类ConditionObject维护的Condition队列(用于支持线程间的协作,提供await,signal,signalAll方法) AQS核心思想 如果被请求的共享资源空闲,那么就将当前请求资源的线程设置为有效的工作线程,将共享资源设置为锁定状态 如果共享资源被占用,就需要一定的阻塞等待唤醒机制来保证锁分配 这个机制主要用CLH队列的变体实现,将暂时获取不到锁的线程加入到队列中 CLH算法轮询前驱节点的状态,这样会耗费处理器资源 AQS没有一直轮询,而是用阻塞等待唤醒机制来节省处理器资源 CLH Craig、Landin and Hagersten队列,单向链表, AQS中的队列是CLH变体的虚拟双向队列(FIFO) AQS通过将每条请求共享资源的线程封装成一个节点来实现锁的分配 AQS使用volatile的int类型的成员变量来表示同步状态, 通过内置的FIFO队列来完成资源获取的排队工作,通过CAS完成对State值的修改 AQS 在线程竞争锁失败后,把线程信息包装成一个节点,加入同步队列 多个线程同时竞争锁失败,都会加入同步队列,使用CAS方式设置同步队列首尾节点的引用 出队列时,首节点的线程在释放同步状态后,将会唤醒后继节点的线程, 并且后继节点的线程在获取到同步状态后将会将自己设置为首节点 设置首节点是通过获取同步状态成功的线程来完成的 因此设置头结点的方法并不需要使用CAS来保证,因为只有一个线程能获取到同步状态 AQS 提供等待通知机制,用来代替传统的Object的wait notify notifyAll 实现线程间的协作 让某些线程一起等待某个条件(Condition) 只有该条件具备时( 调用 signal signalAll方法),这些等待线程才会被唤醒,重新争夺锁
java线程状态及转换 java死锁实例 ReentrantLock原理 基于 wait 和 notifyAll 实现简单的阻塞队列 基于 ReentrantLock Condition await signalAll 实现简单的阻塞队列 Lock和synchronized的区别 synchronized知识点 AQS要点整理 AQS同步队列与条件队列 The java.util.concurrent Synchronizer Framework 翻译 LockSupport简介

上一篇     下一篇
ReentrantLock原理

基于 wait 和 notifyAll 实现简单的阻塞队列

基于 ReentrantLock Condition await signalAll 实现简单的阻塞队列

java死锁实例

SpringBoot启动过程简介

Springboot2 Tomcat自定义配置