原文地址
https://blog.csdn.net/yu280265067/article/details/50986947?utm_source=blogxgwz0
相关解释
CAS原子性操作的原理:
上述栗子可见,最终java调用的是Unsafe类的CAS方法,该方法是native方法,它的实现是C++写的(unsafe.cpp)
public final native boolean compareAndSwapInt(Object var1, long var2, int var4, int var5);
unsafe.cpp实现
UNSAFE_ENTRY(jboolean, Unsafe_CompareAndSwapInt(JNIEnv *env, jobject unsafe, jobject obj, jlong offset, jint e, jint x))
UnsafeWrapper("Unsafe_CompareAndSwapInt");
oop p = JNIHandles::resolve(obj);
jint* addr = (jint *) index_oop_from_field_offset_long(p, offset);
return (jint)(Atomic::cmpxchg(x, addr, e)) == e;
UNSAFE_END
inline jint Atomic::cmpxchg (jint exchange_value, volatile jint* dest, jint compare_value) {
int mp = os::is_MP();
__asm__ volatile (LOCK_IF_MP(%4) "cmpxchgl %1,(%3)"
: "=a" (exchange_value)
: "r" (exchange_value), "a" (compare_value), "r" (dest), "r" (mp)
: "cc", "memory");
return exchange_value;
}
在第三行可以看到,是通过cmpxchgl这个指令在CPU级完成CAS操作的,该指令在多核情况下依旧不能保证原子性
LOCK_IF_MP(%4):在多核的情况下添加一条lock指令;所以多核下相当于lock cmpxchgl ,有了它就能保证原子性了
lock指令会锁定CPU的缓存行或者锁总线
概括:
CAS操作调用的是unsafe类的CAS方法,该方法是native方法,底层实现通过cmpxchgl这个指令在CPU级完成CAS操作的
在多核下还需添加一条lock指令;即lock cmpxchg 来保障原子性;lock指令会锁定CPU的缓存行或者锁总线