深入Java锁机制

一、Synchronized

(一)特点

1、synchronized是Java中实现线程同步的关键字,它提供了互斥性和可见性保证

2、JVM层面锁(内置锁),基于Monitor(对象监视器)实现

3、可重入 (Reentrant Lock),同一线程可多次获取同一把锁,避免死锁

4、悲观锁,线程获取锁前会阻塞其他线程,认为并发冲突频繁,先加锁再操作

5、非公平锁,允许线程"插队"获取锁,提高吞吐量但可能导致饥饿

6、阻塞锁,线程获取锁失败时,进入阻塞状态,编译时自动生成 monitorenter和monitorexit 字节码指令

7、对象级锁,锁定对象实例或代码块,同步非静态方法或 synchronized(this),多个线程竞争同一个对象的锁

方法同步:public synchronized void method()

代码块同步:synchronized(obj) {...}

8、类级锁,锁定类的Class对象或静态同步方法或synchronized(Class.class),所有实例共享同一把锁

(二)结构

可视化工具

JOL (Java Object Layout):通过 jol-core 库打印对象内存布局,直接观察Mark Word

java 复制代码
Object obj = new Object();
System.out.println(ClassLayout.parseInstance(obj).toPrintable());

输出示例(64位无锁状态)

java 复制代码
java.lang.Object object internals:
 OFFSET  SIZE  TYPE DESCRIPTION                               VALUE
      0     4       (object header)                           01 00 00 00 (00000001 00000000 00000000 00000000) (1)
      4     4       (object header)                           00 00 00 00 (00000000 00000000 00000000 00000000) (0)
      8     4       (object header)                           43 c1 00 f8 (01000011 11000001 00000000 11111000) (-134168317)
     12     4       (loss due to the next object alignment)

前8字节为Mark Word(0x0000000000000001,锁标志为01,表示无锁)

Mark Word锁状态转换

(一)JVM 内部优化(synchronized锁升级过程)

无锁 → 偏向锁 → 轻量级锁 → 重量级锁

  1. 无锁状态:初始状态

  2. 偏向锁:无竞争时偏向第一个获取锁的线程

  3. 轻量级锁:多线程竞争不激烈时,通过CAS获取

  4. 重量级锁:竞争激烈时升级为操作系统互斥锁(mutex)

重量级锁依赖于 Monitor 对象(也称为管程或监视器锁),每个 Java 对象都可以关联一个 Monitor 对象。

Monitor 结构

java 复制代码
ObjectMonitor {
    _header       = NULL;    // 对象头
    _count        = 0;        // 重入次数
    _waiters      = 0;        // 等待线程数
    _recursions   = 0;         // 锁重入次数
    _object       = NULL;     // 关联的对象
    _owner        = NULL;    // 持有锁的线程
    _WaitSet      = NULL;     // 处于 wait 状态的线程队列
    _cxq          = NULL;    // 竞争队列
    _EntryList    = NULL;      // 等待锁的线程队列
}

Monitor工作流程图

二、ReentrantLock

(一)特点

1、Java并发包(java.util.concurrent.locks)中的一个可重入互斥锁,通过 Lock接口和实现类提供更灵活的锁操作(如可中断、超时、公平性等)。

2、基于AQS (AbstractQueuedSynchronizer),Java并发包中锁的核心实现框架

3、JUC层面(显式锁Explicit Lock),支持公平/非公平模式

  • ReentrantLock(true):公平锁,按照线程请求顺序获取锁,遵循先到先得原则(FIFO)

  • ReentrantLock(false):默认非公平锁,允许线程"插队"获取锁,提高吞吐量但可能导致饥饿

4、可重入 (Reentrant Lock),同一线程可多次获取同一把锁,避免死锁

5、条件锁 (Condition Lock),基于条件变量实现线程等待/通知机制,条件变量支持newCondition()

6、悲观锁,认为并发冲突频繁,线程获取锁前会阻塞其他线程,先加锁再操作

7、对象级锁锁定对象实例或代码块,多个线程竞争同一个对象的锁。

8、阻塞锁,线程获取锁失败时,进入阻塞状态,可中断的获取锁lockInterruptibly(),超时获取锁tryLock(long timeout, TimeUnit unit)

(二)类继承关系

java 复制代码
java.util.concurrent.locks.ReentrantLock
├── FairSync (公平锁)
└── NonfairSync (非公平锁)
    └── Sync (抽象基类)
        └── AbstractQueuedSynchronizer (AQS)

1、非公平锁实现

nonfairTryAcquire (非公平锁尝试获取)

java 复制代码
final boolean nonfairTryAcquire(int acquires) {
    final Thread current = Thread.currentThread();
    int c = getState();
    if (c == 0) { // 锁未被持有
        if (compareAndSetState(0, acquires)) { // CAS获取
            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;
    }
    return false;
}

tryRelease (尝试释放锁)

java 复制代码
protected final boolean tryRelease(int releases) {
    int c = getState() - releases;
    if (Thread.currentThread() != getExclusiveOwnerThread())
        throw new IllegalMonitorStateException();
    boolean free = false;
    // 计数器归零
    if (c == 0) {
        free = true;
        // 清除持有线程
        setExclusiveOwnerThread(null);
    }
    // 更新状态
    setState(c);
    return free;
}

2、公平锁实现

java 复制代码
protected final boolean tryAcquire(int acquires) {
    final Thread current = Thread.currentThread();
    int c = getState();
    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;
    }
    return false;
}

关键区别:

非公平锁:新线程可以直接插队尝试获取锁

公平锁:必须检查队列中是否有等待线程,遵循FIFO原则

公平与非公平锁对比

特性 公平锁 非公平锁
锁获取顺序 严格按照请求顺序 可能插队
吞吐量 较低 较高
避免线程饥饿
实现方式 请求时检查队列 先尝试获取,失败再入队

(三)AQS核心机制

1、同步状态管理

state 字段:32位整型,表示同步状态

独占模式:0表示未获取,1表示已获取,>1表示重入

共享模式:表示可被多个线程获取的许可数量

2、FIFO等待队列

CLH 队列变种:双向链表实现的FIFO队列

节点状态:

CANCELLED=1:线程已取消等待

SIGNAL=-1:后继节点需要被唤醒

CONDITION=-2:节点在条件队列中

PROPAGATE=-3:共享模式下传播释放信号

3、独占模式流程

java 复制代码
public final void acquire(int arg) {
    if (!tryAcquire(arg) && // 尝试获取
        acquireQueued(addWaiter(Node.EXCLUSIVE), arg)) // 获取失败则入队
        selfInterrupt();
}

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)) { // 如果是head的后继
                setHead(node); // 设置自己为head
                p.next = null; // 帮助GC
                failed = false;
                return interrupted;
            }
            if (shouldParkAfterFailedAcquire(p, node) && // 检查是否需要阻塞
                parkAndCheckInterrupt()) // 阻塞线程
                interrupted = true;
        }
    } finally {
        if (failed)
            cancelAcquire(node);
    }
}

4、共享模式流程

java 复制代码
public final void acquireShared(int arg) {
    if (tryAcquireShared(arg) < 0) // 尝试获取共享许可
        doAcquireShared(arg); // 获取失败则入队
}

private void doAcquireShared(int arg) {
    final Node node = addWaiter(Node.SHARED); // 加入共享节点
    boolean failed = true;
    try {
        boolean interrupted = false;
        for (;;) {
            final Node p = node.predecessor();
            if (p == head) {
                int r = tryAcquireShared(arg); // 尝试获取
                if (r >= 0) { // 成功
                    setHeadAndPropagate(node, r); // 设置head并传播信号
                    p.next = null;
                    if (interrupted)
                        selfInterrupt();
                    failed = false;
                    return;
                }
            }
            if (shouldParkAfterFailedAcquire(p, node) &&
                parkAndCheckInterrupt())
                interrupted = true;
        }
    } finally {
        if (failed)
            cancelAcquire(node);
    }
}

共享模式与独占模式对比

关键方法说明

tryAcquire(int):独占模式获取同步状态(需子类实现)

tryRelease(int):独占模式释放同步状态(需子类实现)

tryAcquireShared(int):共享模式获取同步状态(需子类实现)

tryReleaseShared(int):共享模式释放同步状态(需子类实现)

isHeldExclusively():判断当前线程是否独占同步状态(需子类实现)

(四)AQS在JUC中应用

ReentrantLock与synchronized对比

特性 ReentrantLock synchronized
实现机制 AQS+CAS JVM内置monitor
锁获取方式 显式lock()/unlock() 隐式(代码块/方法)
公平性 可配置公平/非公平 非公平
可中断 支持(lockInterruptibly) 不支持
超时机制 支持(tryLock) 不支持
条件变量 支持(多个Condition) 单一wait/notify
性能 高竞争下表现更好 优化后性能相当

三、ReentrantReadWriteLock

JUC层面,显式锁 (Explicit Lock),读写锁 (Read-Write Lock),分读锁和写锁,允许多线程并发读,但写操作独占,java.util.concurrent.locks包下的锁,通过Lock接口和实现类提供更灵活的锁操作(如可中断、超时、公平性等)。

(一)特点

1、读写分离:读锁(共享锁)和写锁(独占锁)分离

2、重入性:支持重入,同一个线程可以多次获取同一把锁

3、公平性选择:支持公平和非公平两种模式

4、锁降级:允许从写锁降级为读锁

(二)核心组件

Sync:抽象同步器,继承自AQS(AbstractQueuedSynchronizer)

FairSync:公平锁实现

NonfairSync:非公平锁实现

Holder:持有锁的线程信息

State:同步状态,高16位表示读锁状态,低16位表示写锁状态

(三)同步状态设计

ReentrantReadWriteLock 使用一个 32 位的 int 类型的 state 来表示锁状态

(四)代码查看

1、读锁获取 (doAcquireShared)

java 复制代码
protected final int tryAcquireShared(int unused) {
    Thread current = Thread.currentThread();
    int c = getState();
    // 检查写锁是否被其他线程持有
    if (exclusiveCount(c) != 0 &&
        getExclusiveOwnerThread() != current)
        return -1;
        
    int r = sharedCount(c);
    if (!readerShouldBlock() &&
        r < MAX_COUNT &&
        compareAndSetState(c, c + SHARED_UNIT)) {
        // 成功获取读锁
        if (r == 0) {
            firstReader = current;
            firstReaderHoldCount = 1;
        } else if (firstReader == current) {
            firstReaderHoldCount++;
        } else {
            HoldCounter rh = cachedHoldCounter;
            if (rh == null || rh.tid != getThreadId(current))
                cachedHoldCounter = rh = readHolds.get();
            else if (rh.count == 0)
                readHolds.set(rh);
            rh.count++;
        }
        return 1;
    }
    // 获取失败,进入等待队列
    return fullTryAcquireShared(current);
}

2、写锁获取 (tryAcquire)

java 复制代码
protected final boolean tryAcquire(int acquires) {
    Thread current = Thread.currentThread();
    int c = getState();
    int w = exclusiveCount(c);
    if (c != 0) {
        // 存在读锁或写锁被其他线程持有
        if (w == 0 || current != getExclusiveOwnerThread())
            return false;
        if (w + exclusiveCount(acquires) > MAX_COUNT)
            throw new Error("Maximum lock count exceeded");
        // 重入
        setState(c + acquires);
        return true;
    }
    // 检查是否应该阻塞(公平性)
    if (writerShouldBlock() ||
        !compareAndSetState(c, c + acquires))
        return false;
    setExclusiveOwnerThread(current);
    return true;
}

(五)流程图

四、StampedLock

StampedLock (Java 8+)改进的读写锁,它提供了比ReentrantReadWriteLock更灵活的锁操作,特别适合读多写少的场景。读锁不阻塞写锁(通过版本戳机制),支持锁升级和降级,性能优于ReentrantReadWriteLock在高并发读场景

(一)支持三种模式

1、写锁(exclusive lock)独占锁

获取:long stamp = lock.writeLock()

释放:lock.unlockWrite(stamp)

特点:独占锁,与其他所有模式互斥

2、悲观读锁(pessimistic read lock)类似ReadWriteLock的读锁,共享锁

获取:long stamp = lock.readLock()

释放:lock.unlockRead(stamp)

特点:共享锁,与写锁互斥,与其他读锁不互斥

3、乐观读(optimistic read)不阻塞写操作,需后续验证

获取:long stamp = lock.tryOptimisticRead()

验证:lock.validate(stamp)

特点:不阻塞,没有真正的锁获取,只是获取一个戳记用于后续验证

(二)数据结构

StampedLock内部使用一个long类型的state变量来存储所有状态信息,通过位运算来区分不同状态

状态转换图

(三)代码查看

1、乐观读

乐观读不获取实际锁,只是读取当前状态作为"戳记"(stamp)

java 复制代码
public long tryOptimisticRead() {
    long stamp = state;
    // 检查是否有写锁
    if ((stamp & WBIT) != 0L) {
        return 0L; // 有写锁则返回0表示失败
    }
    return stamp; // 返回当前状态作为戳记
}

2、悲观读锁

悲观读锁会阻塞写操作

java 复制代码
public long readLock() {
    long s, next; // 忽略重试逻辑
    for (;;) {
        s = state;
        // 检查是否有写锁或写线程在等待
        if (((s & WBIT) != 0L) || ((s & (WBIT - 1)) != 0L)) {
            // 阻塞等待
        } else if (U.compareAndSwapLong(this, STATE, s, next = s + RUNIT)) {
            return next;
        }
    }
}

3、写锁

写锁是独占锁

java 复制代码
public long writeLock() {
    long s, next; // 忽略重试逻辑
    for (;;) {
        s = state;
        // 检查是否有任何读锁或写锁
        if ((s & WBIT) != 0L || (s != 0L)) {
            // 阻塞等待
        } else if (U.compareAndSwapLong(this, STATE, s, next = s + WBIT)) {
            return next;
        }
    }
}

五、Atomic

Atomic(原子性)操作是指不可中断的一个或一系列操作,这些操作要么全部执行成功,要么全部不执行,不会出现执行到中间状态的情况

(一)CPU支持

Atomic操作的实现主要依赖于CPU提供的原子指令

1、比较并交换 (CAS - Compare And Swap)

指令示例:x86的CMPXCHG

操作:比较内存值与期望值,如果相同则替换为新值

2、原子加载-存储

指令示例:x86的MOV带LOCK 前缀

操作:保证加载或存储操作的原子性

3、其他原子指令

递增/递减(INC/DEC 带 LOCK)

交换(XCHG)

(二)处理器

不同处理器架构实现原子操作的方式不同

架构 实现方式
x86 使用LOCK前缀指令锁定总线或缓存行
ARM 使用LL/SC指令对
RISC-V 使用AMO(Atomic Memory Operation)指令

(三)CAS(Compare And Swap)原理

1、Java中的CAS

java 复制代码
public final class Unsafe {
    public final native boolean compareAndSwapObject(
        Object o, long offset, Object expected, Object x);
        
    public final native boolean compareAndSwapInt(
        Object o, long offset, int expected, int x);
        
    public final native boolean compareAndSwapLong(
        Object o, long offset, long expected, long x);
}

2、CAS典型应用AtomicInteger实现

java 复制代码
public class AtomicInteger {
    private volatile int value;
    private static final Unsafe unsafe = Unsafe.getUnsafe();
    private static final long valueOffset;
    
    static {
        try {
            valueOffset = unsafe.objectFieldOffset
                (AtomicInteger.class.getDeclaredField("value"));
        } catch (Exception ex) { throw new Error(ex); }
    }
    
    public final boolean compareAndSet(int expect, int update) {
        return unsafe.compareAndSwapInt(this, valueOffset, expect, update);
    }
}

3、ABA问题

初始: A → B → A (内存值变化过程)

Thread1 看到 A,准备更新为C

Thread2 快速将 A→B→A

Thread1 认为值没变(还是 A),执行CAS成功

但实际中间经历了变化

解决方案

版本号/时间戳(如 Java 的 AtomicStampedReference)

危险指针(如 C++ 的 hazard_pointer)

4、不同语言Atomic实现

语言 底层机制 典型类/函数
Java Unsafe + CAS AtomicInteger, AtomicReference
C++11 std::atomic compare_exchange_strong
Go runtime + CAS sync/atomic包
Rust Atomic*类型 std::sync::atomic

(四)LL/SC (Load-Linked/Store-Conditional) 加载链接/条件存储

LL/SC(Load-Linked/Store-Conditional)是现代 CPU(如 ARM、PowerPC、RISC-V)提供的一种原子操作机制,用于实现无锁同步(lock-free programming)。它与 CAS(Compare-And-Swap) 类似,采用"乐观读取-条件写入"的方式,避免了CAS的ABA 问题。

1、LL/SC指令组成

LL(Load-Linked)

读取内存中的值,并 标记该内存位置(类似于"监视"该地址)。

如果其他线程修改了该地址,标记会失效。

SC(Store-Conditional)

尝试将新值写入 LL 标记的内存位置。

仅当该地址未被其他线程修改过 时,写入成功(返回 success),否则失败(返回 fail)。

如果失败,通常需要重新执行 LL 和 SC 循环。

2、不同架构实现差异

架构 LL指令 SC指令 保留粒度
ARM LDREX STREX 通常缓存行大小
MIPS LL SC 实现定义
PowerPC lwarx stwcx. 缓存行
RISC-V LR.W/D SC.W/D 实现定义

3、LL/SC vs CAS

特性 LL/SC CAS
关键指令 LL/SC 或 LDXR/STXR CMPXCHG
适用CPU ARM、RISC-V、PowerPC x86、AMD64
灵活性 更高(可在两条指令间插入其他操作) 较低
伪失败 更常见(因监控粒度较大) 较少
工作方式 乐观读取+条件写入 比较并交换
ABA问题 天然避免(SC会检测修改) 可能受ABA问题影响
性能 高并发时可能更好(减少竞争) 高竞争时可能自旋较多

(五)内存屏障(Memory Barriers)保证指令执行顺序

内存屏障(Memory Barrier,也称内存栅栏)是一种CPU指令,用于控制指令执行顺序和内存可见性,解决多核处理器中的内存乱序问题。

1、内存屏障核心

1)防止指令重排序

编译器优化:编译器可能调整指令顺序以提高性能(如将写操作移到循环外)。

CPU 乱序执行:现代 CPU 采用乱序执行(Out-of-Order Execution)和分支预测,导致指令实际执行顺序与代码顺序不一致。

内存屏障:强制 CPU 和编译器 按顺序执行屏障前后的指令,避免乱序。

2)保证内存可见性

缓存一致性协议(MESI):多核 CPU 通过缓存一致性协议保证缓存同步,但可能存在延迟。

内存屏障:强制刷新 CPU 缓存,确保屏障前的写操作对其他线程可见,屏障后的读操作能读取最新值。

MESI状态

状态 含义
Modified(M) 缓存行已被当前核心修改,且未写回主存,其他核心的缓存行必须为 Invalid
Exclusive(E) 缓存行未被修改,且仅当前核心持有,其他核心无此缓存行(可能主存未更新)
Shared(S) 缓存行未被修改,且多个核心共享此缓存行(内容与主存一致)
Invalid(I) 缓存行无效(未加载或已被其他核心修改)

2、内存屏障分类

内存屏障分为 4 种基本类型,根据作用方向(读/写)和屏障强度(全屏障/单向屏障)组合而成

类型 作用 典型指令
LoadLoad 保证前面的Load先于后面的Load LOAD_A; Barrier; LOAD_B
StoreStore 保证前面的Store先于后面的Store STORE_A; Barrier; STORE_B
LoadStore 保证前面的Load先于后面的Store LOAD_A; Barrier; STORE_B
StoreLoad 保证前面的Store先于后面的Load STORE_A; Barrier; LOAD_B

Load = 读,Store = 写

屏障名称格式:[屏障前操作][屏障后操作]

如 StoreLoad = 确保写操作在读操作前完成

强度分类

完全屏障(Full Barrier) > 获取屏障(Acquire) > 释放屏障(Release) > 编译屏障

3、内存屏障与原子操作

原子操作通常隐含内存屏障:

原子读:包含获取语义(Acquire)

原子写:包含释放语义(Release)

RMW操作:包含完全屏障(Full Barrier)

4、内存屏障的作用

1)无内存屏障时的乱序问题

java 复制代码
// 线程1
x = 1;          // 写操作
flag = true;    // 写操作
// 线程2
if (flag) {     // 读操作
    print(x);   // 读操作
}

可能的重排序结果(导致线程2打印 x=0)

java 复制代码
线程1: flag = true; x = 1;  // 编译器/CPU 调整顺序
线程2: if (flag) { print(0); } // 读取到旧值

2)插入StoreLoad Barrier后的正确顺序

java 复制代码
// 线程1
x = 1;
StoreLoad Barrier;  // 确保 x=1 对其他线程可见后再设置 flag
flag = true;
// 线程2
if (flag) {
    LoadLoad Barrier;  // 确保读取 flag 后再读取 x
    print(x);
}

执行顺序保证

线程1 的 x=1 必须在线程2 读取 flag 前完成。

线程2 读取 flag 后,必须读取最新的 x 值。

3)Java内存模型(JMM)

volatile 关键字:

编译器插入 StoreLoad Barrier(mfence 或 lock addl)。

确保写操作对其他线程立即可见。

synchronized 关键字:

进入同步块时插入 LoadLoad + StoreStore 屏障。

退出同步块时插入 StoreLoad 屏障。

5、内存屏障应用场景

1)无锁数据结构(Lock-Free)

java 复制代码
// 原子引用更新(CAS + 内存屏障)
public class AtomicReference<T> {
    private volatile T value;
    
    public boolean compareAndSet(T expected, T newValue) {
        // CAS 操作隐含 StoreLoad 屏障
        return unsafe.compareAndSwapObject(this, valueOffset, expected, newValue);
    }
}

2)双检锁单例模式(DCL)

java 复制代码
public class Singleton {
    private static volatile Singleton instance;
    public static Singleton getInstance() {
        if (instance == null) {                 // 第一次检查
            synchronized (Singleton.class) {
                if (instance == null) {         // 第二次检查
                    instance = new Singleton(); // 写操作 + 内存屏障
                }
            }
        }
        return instance;
    }
}

volatile 作用:

防止 instance = new Singleton() 被重排(对象未初始化完成就被发布)。

3)JVM 内部实现

Unsafe.putOrderedObject():

仅保证写操作顺序(StoreStore),不保证可见性(比 volatile 更轻量)。

Unsafe.fullFence():

插入全屏障(StoreLoad)

6、内存屏障总结

屏障类型 作用 典型场景
LoadLoad 防止读操作重排到读操作之前 无锁读、volatile 读
StoreStore 防止写操作重排到写操作之后 无锁写、volatile 写
StoreLoad 防止写操作重排到读操作之前 CAS、双检锁、volatile 写读
全屏障 防止所有读写操作重排 同步块退出、JVM 内部同步

六、CountDownLatch / CyclicBarrier / Semaphore

虽非传统锁,但用于协调线程执行,属于广义同步工具

七、LockSupport

提供更底层的线程阻塞/唤醒支持如 park()/unpark()

八、选择建议

场景 建议
低竞争、简单同步 Synchronized (JVM 会自动优化)、内置锁
高竞争、灵活控制 ReentrantLock (可设置公平性)、显式锁
读多写少 ReentrantReadWriteLock
高并发读 StampedLock(乐观读)、乐观锁
原子操作、无锁编程 Atomic类+ CAS、乐观锁

九、 参考

1、 官网地址OpenJDK Wiki

wiki.openjdk.org/display/Hot...

2、 OpenJDK 官方文档 AQS JavaDoc

docs.oracle.com/en/java/jav...

3、 Doug Lea AQS 论文 (作者原始设计文档)

gee.cs.oswego.edu/dl/papers/a...

4、 OpenJDK 源代码 GitHub AQS源码

github.com/openjdk/jdk...

5、 ARM官方文档

developer.arm.com/documentati...

搜索LDXR/STXR,即ARM的LL/SC实现,关键指令:

LDXR(Load-Exclusive,相当于 LL)

STXR(Store-Exclusive,相当于 SC)

6、 RISC-V官方文档

riscv.org/specificati...

搜索 LR.W/SC.W,关键指令:

LR.W(Load Reserved,相当于 LL)

SC.W(Store Conditional,相当于 SC)

7、 PowerPC官方文档

openpowerfoundation.org/specificati...

搜索 lwarx/stwcx,关键指令:

lwarx(Load with Reserve,相当于 LL)

stwcx(Store Conditional Word,相当于 SC)

相关推荐
胚芽鞘68115 分钟前
关于java项目中maven的理解
java·数据库·maven
岁忧1 小时前
(LeetCode 面试经典 150 题 ) 11. 盛最多水的容器 (贪心+双指针)
java·c++·算法·leetcode·面试·go
CJi0NG1 小时前
【自用】JavaSE--算法、正则表达式、异常
java
Hellyc2 小时前
用户查询优惠券之缓存击穿
java·redis·缓存
今天又在摸鱼2 小时前
Maven
java·maven
老马啸西风2 小时前
maven 发布到中央仓库常用脚本-02
java·maven
代码的余温2 小时前
MyBatis集成Logback日志全攻略
java·tomcat·mybatis·logback
一只叫煤球的猫4 小时前
【🤣离谱整活】我写了一篇程序员掉进 Java 异世界的短篇小说
java·后端·程序员
斐波娜娜4 小时前
Maven详解
java·开发语言·maven
Bug退退退1234 小时前
RabbitMQ 高级特性之事务
java·分布式·spring·rabbitmq