看图学源码 之 Atomic 类源码浅析一(cas + 自旋操作的 AtomicXXX原子类)

Atomic

针对基本数据类型的单个变量

AtomicInteger
// 就是对  value 执行操作
public class AtomicInteger extends Number implements java.io.Serializable {
  ...
    // 拿到 Unsafe  类  
   private static final Unsafe unsafe = Unsafe.getUnsafe();
  
  // 偏移量: 字段相对于对象内存地址的偏移量
   private static final long valueOffset;
  

   static {
       try {
         // 反射的方式获取 value 的偏移量  这个偏移量可以用于后续的无锁操作
           valueOffset = unsafe.objectFieldOffset(AtomicInteger.class.getDeclaredField("value"));
       } catch (Exception ex) { throw new Error(ex); }
   }

   private volatile int value;
  
  
  // 其他的方法都是直接调用 native 的方法实现的,如:getAndIncrement、getAndDecrement、compareAndSet、getAndSet等
  ...
    // 以此为例
    
    /*
    如果指定位置上的当前值==预期值,则自动将该值设置为给定的更新值。
    形参:
    expect期望值 update ——新值
    返回值:
    如果cas 成功则为true 。返回 False 表示指定位置上的实际值不等于期望值。
    */
     public final boolean compareAndSet(int expect, int update) {
        return unsafe.compareAndSwapInt(this, valueOffset, expect, update);
    }
    
    
    
}
AtomicBoolean
public class AtomicBoolean implements java.io.Serializable {
   ...
    // setup to use Unsafe.compareAndSwapInt for updates
    private static final Unsafe unsafe = Unsafe.getUnsafe();
    private static final long valueOffset;

    static {
        try {
            valueOffset = unsafe.objectFieldOffset(AtomicBoolean.class.getDeclaredField("value"));
        } catch (Exception ex) { throw new Error(ex); }
    }

    private volatile int value;
  ...
    
    
    //如果当前值==预期值,则自动将该值设置为给定的更新值。
    public final boolean compareAndSet(boolean expect, boolean update) {  // 这里的是 boolean 类型的值
    // 将boolean   转为 int  值进行 cas 
        int e = expect ? 1 : 0;
        int u = update ? 1 : 0;
        return unsafe.compareAndSwapInt(this, valueOffset, e, u);
    }
}
AtomicLong
public class  AtomicLong extends Number implements java.io.Serializable {
    private static final long serialVersionUID = 1927816293512124184L;

    // setup to use Unsafe.compareAndSwapLong for updates
    private static final Unsafe unsafe = Unsafe.getUnsafe();
    private static final long valueOffset;

    /**
     * 
     记录底层 JVM 是否支持 long 的无锁compareAndSwap。
     虽然 Unsafe.compareAndSwapLong 方法在任一情况下都有效,但应在 Java 级别处理某些构造以避免锁定用户可见的锁。
     */
    static final boolean VM_SUPPORTS_LONG_CAS = VMSupportsCS8();

    /**
     返回底层 JVM 是否支持 long 的无锁 CompareAndSet。仅调用一次并缓存在 VM_SUPPORTS_LONG_CAS 中。
     */
    private static native boolean VMSupportsCS8();

    static {
        try {
            valueOffset = unsafe.objectFieldOffset
                (AtomicLong.class.getDeclaredField("value"));
        } catch (Exception ex) { throw new Error(ex); }
    }

    private volatile long value;
 ...
   /* 
   	如果当前值==预期值,则自动将该值设置为给定的更新值。
   	形参:
    expect期望值 update ——新值
    返回值:
    如果成功则为true 。返回 False 表示实际值不等于期望值。
   */
 		public final boolean compareAndSet(long expect, long update) {
        return unsafe.compareAndSwapLong(this, valueOffset, expect, update);
    } 
 ... 
}

针对引用类型的单个变量

通过对 Object中的属性进行反射 + CAS 支持属性原子操作

AtomicReference
public class AtomicReference<V> implements java.io.Serializable {
    private static final long serialVersionUID = -1848883965231344442L;

    private static final Unsafe unsafe = Unsafe.getUnsafe();
    private static final long valueOffset;

    static {
        try {
            valueOffset = unsafe.objectFieldOffset
                (AtomicReference.class.getDeclaredField("value"));
        } catch (Exception ex) { throw new Error(ex); }
    }

  private volatile V value;
  ...
	public final boolean compareAndSet(V expect, V update) {
      return unsafe.compareAndSwapObject(this, valueOffset, expect, update);
  }
  ...
}
AtomicStampedReference
public class AtomicStampedReference<V> {

    private static class Pair<T> {
        final T reference;
        final int stamp;   // 解决了 cas 的 ABA 问题
        private Pair(T reference, int stamp) {
            this.reference = reference;
            this.stamp = stamp;
        }
        static <T> Pair<T> of(T reference, int stamp) {
            return new Pair<T>(reference, stamp);
        }
    }

    private volatile Pair<V> pair;
  
  ...
    /*
    如果当前引用==到预期引用并且当前标记等于预期标记,则以原子方式将引用和标记的值设置为给定更新值。
    形参:
    expectedReference – 参考的预期值
    newReference – 参考的新值
    expectedStamp – 邮票的预期值
    newStamp – 邮票的新值
    返回值:
    如果成功则为true
    */
   public boolean compareAndSet(V   expectedReference,
                                 V   newReference,
                                 int expectedStamp,
                                 int newStamp) {
       // 将当前的pair赋值给变量current
        Pair<V> current = pair;
        return
            expectedReference == current.reference && //当前的值是 预期的值
            expectedStamp == current.stamp && // 当前的stamp 也是预期的值
            ((newReference == current.reference && // 新值是 当前的值
              newStamp == current.stamp) ||  // stamp 的值是 当前的值
             //前两个都是false 那么就 cas 的 将current替换为Pair.of(newReference, newStamp)
             casPair(current, Pair.of(newReference, newStamp)));
    }
  ...
    /*
    使用CAS操作来原子性地更新AtomicStampedReference对象中的pair字段的值。
    */
    // 获取了一个用于执行底层操作的Unsafe实例。
    private static final sun.misc.Unsafe UNSAFE = sun.misc.Unsafe.getUnsafe();
  //获取了pair字段在AtomicStampedReference类中的偏移量。
private static final long pairOffset = objectFieldOffset(UNSAFE, "pair", AtomicStampedReference.class);

  // 使用UNSAFE.compareAndSwapObject方法来比较并交换对象的pair字段的值。如果当前的pair字段的值等于cmp,则将其更新为val并返回true,否则返回false。
    private boolean casPair(Pair<V> cmp, Pair<V> val) {
        return UNSAFE.compareAndSwapObject(this, pairOffset, cmp, val);
    }
  
  //获取指定类中指定字段的偏移量。
    static long objectFieldOffset(sun.misc.Unsafe UNSAFE,
                                  String field, Class<?> klazz) {
        try {
          //通过反射获取字段对象,然后使用UNSAFE.objectFieldOffset方法获取字段的偏移量。
            return UNSAFE.objectFieldOffset(klazz.getDeclaredField(field));
        } catch (NoSuchFieldException e) {
          // 如果字段不存在,则抛出NoSuchFieldError异常。
            NoSuchFieldError error = new NoSuchFieldError(field);
            error.initCause(e);
            throw error;
        }
    }
}
AtomicMarkableReference
public class AtomicMarkableReference<V> {

    private static class Pair<T> {
        final T reference;
        final boolean mark;
        private Pair(T reference, boolean mark) {
            this.reference = reference;
            this.mark = mark;
        }
        static <T> Pair<T> of(T reference, boolean mark) {
            return new Pair<T>(reference, mark);
        }
    }

    private volatile Pair<V> pair;
    
  ...
    /*
    如果当前引用==到预期引用并且当前标记等于预期标记,则以原子方式将引用和标记的值设置为给定更新值。
    形参:
    expectedReference – 参考的预期值 newReference – 参考的新值 expectedMark – 标记的期望值 newMark – 标记的新值
    返回值:
    如果成功则为true
    */
    public boolean compareAndSet(V       expectedReference,
                                 V       newReference,
                                 boolean expectedMark,
                                 boolean newMark) {
        Pair<V> current = pair;
        return
            expectedReference == current.reference &&
            expectedMark == current.mark &&
            ((newReference == current.reference &&
              newMark == current.mark) ||
             casPair(current, Pair.of(newReference, newMark)));
    }
  ...
    
    private static final sun.misc.Unsafe UNSAFE = sun.misc.Unsafe.getUnsafe();
    private static final long pairOffset =
        objectFieldOffset(UNSAFE, "pair", AtomicMarkableReference.class);

    private boolean casPair(Pair<V> cmp, Pair<V> val) {
        return UNSAFE.compareAndSwapObject(this, pairOffset, cmp, val);
    }

    static long objectFieldOffset(sun.misc.Unsafe UNSAFE,
                                  String field, Class<?> klazz) {
        try {
            return UNSAFE.objectFieldOffset(klazz.getDeclaredField(field));
        } catch (NoSuchFieldException e) {
            // Convert Exception to corresponding Error
            NoSuchFieldError error = new NoSuchFieldError(field);
            error.initCause(e);
            throw error;
        }
    }
}

针对的是多个变量

都是通过下标去操作数组中的元素

AtomicIntegerArray
public class AtomicIntegerArray implements java.io.Serializable {
    private static final long serialVersionUID = 2862133569453604235L;

    private static final Unsafe unsafe = Unsafe.getUnsafe();
    private static final int base = unsafe.arrayBaseOffset(int[].class);
    private static final int shift;
    private final int[] array;

  // 计算int数组的元素大小,并确定位移量
    static {
      // 使用unsafe.arrayIndexScale(int[].class)函数获取int数组元素的大小,存储在变量scale中。
        int scale = unsafe.arrayIndexScale(int[].class);
      // 它通过检查scale是否是2的幂次方来确保元素大小是2的幂次方。如果不是,就会抛出一个错误。
        if ((scale & (scale - 1)) != 0)
            throw new Error("data type scale not a power of two");
      // 31 - Integer.numberOfLeadingZeros(scale)函数计算scale的二进制表示中前导零的数量,
      // 得到位移量,并将结果存储在shift变量中。
        shift = 31 - Integer.numberOfLeadingZeros(scale);
    }
  
  ...
    /*
    如果当前值==预期值,则自动将位置i处的元素设置为给定的更新值。
    形参:
    i – 索引   expect期望值 update ——新值
    返回值:
    如果成功则为true 。返回 False 表示实际值不等于期望值。
    */
    public final boolean compareAndSet(int i, int expect, int update) {
        return compareAndSetRaw(checkedByteOffset(i), expect, update);
    }

    private boolean compareAndSetRaw(long offset, int expect, int update) {
        return unsafe.compareAndSwapInt(array, offset, expect, update);
    }
  
    //接受一个整数参数i,并返回一个长整型值。
     private long checkedByteOffset(int i) {
//检查参数i是否小于0或大于等于数组array的长度。如果是,则抛出一个IndexOutOfBoundsException异常,异常信息中包含索引i的值。
        if (i < 0 || i >= array.length)
            throw new IndexOutOfBoundsException("index " + i);
		//调用 byteOffset(i) 来计算并返回字节偏移量
        return byteOffset(i);
    }
  // 将整数 i 左移 shift 位,并将结果与变量 base 相加,然后将其转换为长整型值返回
    private static long byteOffset(int i) {
        return ((long) i << shift) + base;
    }
    ...
}
AtomicLongArray
public class AtomicLongArray implements java.io.Serializable {
    private static final long serialVersionUID = -2308431214976778248L;

    private static final Unsafe unsafe = Unsafe.getUnsafe();
    private static final int base = unsafe.arrayBaseOffset(long[].class);
    private static final int shift;
    private final long[] array;

    static {
        int scale = unsafe.arrayIndexScale(long[].class);
        if ((scale & (scale - 1)) != 0)
            throw new Error("data type scale not a power of two");
        shift = 31 - Integer.numberOfLeadingZeros(scale);
    }

    private long checkedByteOffset(int i) {
        if (i < 0 || i >= array.length)
            throw new IndexOutOfBoundsException("index " + i);

        return byteOffset(i);
    }
    
    private static long byteOffset(int i) {
        return ((long) i << shift) + base;
    }
  
  /*
    如果当前值==预期值,则自动将位置i处的元素设置为给定的更新值。
    形参:
    i – 索引 expect期望值 update ——新值
    返回值:
    如果成功则为true 。返回 False 表示实际值不等于期望值。
  */ 
    public final boolean compareAndSet(int i, long expect, long update) {
        return compareAndSetRaw(checkedByteOffset(i), expect, update);
    }

    private boolean compareAndSetRaw(long offset, long expect, long update) {
        return unsafe.compareAndSwapLong(array, offset, expect, update);
    }
  ...
}
AtomicReferenceArray
public class AtomicReferenceArray<E> implements java.io.Serializable {
    private static final long serialVersionUID = -6209656149925076980L;

    private static final Unsafe unsafe;
    private static final int base;
    private static final int shift;
    private static final long arrayFieldOffset;
    private final Object[] array; // must have exact type Object[]

  // 获取一些与数组操作相关的参数,并进行初始化
    static {
        try {
          // 通过 Unsafe.getUnsafe() 方法获取一个 Unsafe 对象的实例,并将其赋值给静态变量 unsafe。
            unsafe = Unsafe.getUnsafe();
          // 使用 unsafe.objectFieldOffset() 方法获取 AtomicReferenceArray 类中名为 "array" 的字段的偏移量,并将其赋值给静态变量 arrayFieldOffset。
arrayFieldOffset = unsafe.objectFieldOffset(AtomicReferenceArray.class.getDeclaredField("array"));
          // 使用 unsafe.arrayBaseOffset() 方法获取 Object[] 类的基本偏移量,并将其赋值给静态变量 base。
            base = unsafe.arrayBaseOffset(Object[].class);
          //  使用 unsafe.arrayIndexScale() 方法获取 Object[] 类的索引缩放因子,并将其赋值给局部变量 scale。
            int scale = unsafe.arrayIndexScale(Object[].class);
          // 如果 scale 不是 2 的幂次方,则抛出一个 异常
            if ((scale & (scale - 1)) != 0)
                throw new Error("data type scale not a power of two");
          // 根据 scale 计算 shift 的值,该值表示 scale 的二进制表示中最高位的索引。
            shift = 31 - Integer.numberOfLeadingZeros(scale);
        } catch (Exception e) {
            throw new Error(e);
        }
    }
	/*
		如果当前值==预期值,则自动将位置i处的元素设置为给定的更新值。
    形参:
    i – 索引 expect期望值 update ——新值
    返回值:
    如果成功则为true 。返回 False 表示实际值不等于期望值。
   */
    private long checkedByteOffset(int i) {
        if (i < 0 || i >= array.length)
            throw new IndexOutOfBoundsException("index " + i);

        return byteOffset(i);
    }

    private static long byteOffset(int i) {
        return ((long) i << shift) + base;
    }
  ...
    public final boolean compareAndSet(int i, E expect, E update) {
        return compareAndSetRaw(checkedByteOffset(i), expect, update);
    }

    private boolean compareAndSetRaw(long offset, E expect, E update) {
        return unsafe.compareAndSwapObject(array, offset, expect, update);
    }
  ...
}

针对对象类型中的某个属性

AtomicIntegerFieldUpdater
public abstract class AtomicIntegerFieldUpdater<T> {
    @CallerSensitive
    public static <U> AtomicIntegerFieldUpdater<U> newUpdater(Class<U> tclass, String fieldName) {
        return new AtomicIntegerFieldUpdaterImpl<U>(tclass, fieldName, Reflection.getCallerClass());
    }
 
      /*
    如果当前值==预期值,则自动将此更新程序管理的给定对象的字段设置为给定的更新值。该方法相对于对compareAndSet和set其他调用而言保证是原子的,但不一定相对于字段中的其他更改。
    形参:
    obj – 要有条件设置其字段的对象 expect期望值 update ——新值
    返回值:如果成功则为true
    转发: ClassCastException – 如果obj不是拥有构造函数中建立的字段的类的实例
    */
    public abstract boolean compareAndSet(T obj, int expect, int update);
  
  
  
  
      private static final class AtomicIntegerFieldUpdaterImpl<T> extends AtomicIntegerFieldUpdater<T> {
          private static final sun.misc.Unsafe U = sun.misc.Unsafe.getUnsafe();
          private final long offset;

          private final Class<?> cclass;
          private final Class<T> tclass;
        
        // 通过反射获取指定类中的整型字段,并创建一个AtomicIntegerFieldUpdater对象来实现对该字段的原子性更新操作
         AtomicIntegerFieldUpdaterImpl(final Class<T> tclass,
                                      final String fieldName,
                                      final Class<?> caller) {
            final Field field;
            final int modifiers;
            try {
              // 代码通过反射获取了要更新的字段对象,这个字段是在指定的类(tclass)中通过字段名(fieldName)来获取的
                field = AccessController.doPrivileged(
                    new PrivilegedExceptionAction<Field>() {
                        public Field run() throws NoSuchFieldException {
                            return tclass.getDeclaredField(fieldName);
                        }
                    });
              // 检查字段的修饰符(modifiers)来确保它是volatile类型,并且字段的类型是int类型,否则会抛出异常。
                modifiers = field.getModifiers();
              //检查字段的访问权限。如果字段是protected字段,并且访问者(caller)是tclass的子类或者包内的类,那么将使用caller作为访问者,否则使用tclass作为访问者。
                sun.reflect.misc.ReflectUtil.ensureMemberAccess(caller, tclass, null, modifiers);
                ClassLoader cl = tclass.getClassLoader();
                ClassLoader ccl = caller.getClassLoader();
                if ((ccl != null) && (ccl != cl) &&
                    ((cl == null) || !isAncestor(cl, ccl))) {
                    sun.reflect.misc.ReflectUtil.checkPackageAccess(tclass);
                }
            } catch (PrivilegedActionException pae) {
                throw new RuntimeException(pae.getException());
            } catch (Exception ex) {
                throw new RuntimeException(ex);
            }

            if (field.getType() != int.class)
                throw new IllegalArgumentException("Must be integer type");

            if (!Modifier.isVolatile(modifiers))
                throw new IllegalArgumentException("Must be volatile type");

            // 对受保护字段成员的访问仅限于访问类或其子类之一的接收者,并且访问类又必须是受保护成员的定义类的子类(或包兄弟)。如果更新程序引用当前包外部的声明类的受保护字段,则接收者参数将缩小为访问类的类型。
           
            this.cclass = (Modifier.isProtected(modifiers) &&
                           tclass.isAssignableFrom(caller) &&
                           !isSamePackage(tclass, caller))
                          ? caller : tclass;
            this.tclass = tclass;
           //使用UNSAFE.objectFieldOffset(field)方法获取字段的偏移量,并将其保存在offset字段中,以便后续的原子性更新操作中使用。
            this.offset = U.objectFieldOffset(field);
        }
        
        
    public final boolean compareAndSet(T obj, int expect, int update) {
          accessCheck(obj);
          return U.compareAndSwapInt(obj, offset, expect, update);
    }
  //检查目标参数是否是 cclass 的实例。失败时,抛出原因。
    private final void accessCheck(T obj) {
        if (!cclass.isInstance(obj))
              throwAccessCheckException(obj);
    }
  //如果 accessCheck 由于受保护的访问而失败,则抛出访问异常,否则抛出 ClassCastException。
   private final void throwAccessCheckException(T obj) {
            if (cclass == tclass)
                throw new ClassCastException();
            else
                throw new RuntimeException(
                    new IllegalAccessException(
                        "Class " +
                        cclass.getName() +
                        " can not access a protected member of class " +
                        tclass.getName() +
                        " using an instance of " +
                        obj.getClass().getName()));
        }
      }
}
AtomicLongFieldUpdater
public abstract class AtomicLongFieldUpdater<T> {

  @CallerSensitive
    public static <U> AtomicLongFieldUpdater<U> newUpdater(Class<U> tclass,
                                                           String fieldName) {
        Class<?> caller = Reflection.getCallerClass();
        if (AtomicLong.VM_SUPPORTS_LONG_CAS)
            return new CASUpdater<U>(tclass, fieldName, caller);
        else
            return new LockedUpdater<U>(tclass, fieldName, caller);
    }
    
    public abstract boolean compareAndSet(T obj, long expect, long update);
     
     
    private static final class CASUpdater<T> extends AtomicLongFieldUpdater<T> {
    	 private static final sun.misc.Unsafe U = sun.misc.Unsafe.getUnsafe();
       private final long offset;
       private final Class<?> cclass;
       private final Class<T> tclass;
       CASUpdater(final Class<T> tclass, final String fieldName,
                   final Class<?> caller) {
            final Field field;
            final int modifiers;
            try {
                field = AccessController.doPrivileged(
                    new PrivilegedExceptionAction<Field>() {
                        public Field run() throws NoSuchFieldException {
                            return tclass.getDeclaredField(fieldName);
                        }
                    });
                modifiers = field.getModifiers();
                sun.reflect.misc.ReflectUtil.ensureMemberAccess(
                    caller, tclass, null, modifiers);
                ClassLoader cl = tclass.getClassLoader();
                ClassLoader ccl = caller.getClassLoader();
                if ((ccl != null) && (ccl != cl) &&
                    ((cl == null) || !isAncestor(cl, ccl))) {
                    sun.reflect.misc.ReflectUtil.checkPackageAccess(tclass);
                }
            } catch (PrivilegedActionException pae) {
                throw new RuntimeException(pae.getException());
            } catch (Exception ex) {
                throw new RuntimeException(ex);
            }

            if (field.getType() != long.class)
                throw new IllegalArgumentException("Must be long type");

            if (!Modifier.isVolatile(modifiers))
                throw new IllegalArgumentException("Must be volatile type");

            // Access to protected field members is restricted to receivers only
            // of the accessing class, or one of its subclasses, and the
            // accessing class must in turn be a subclass (or package sibling)
            // of the protected member's defining class.
            // If the updater refers to a protected field of a declaring class
            // outside the current package, the receiver argument will be
            // narrowed to the type of the accessing class.
            this.cclass = (Modifier.isProtected(modifiers) &&
                           tclass.isAssignableFrom(caller) &&
                           !isSamePackage(tclass, caller))
                          ? caller : tclass;
            this.tclass = tclass;
            this.offset = U.objectFieldOffset(field);
        }
        
        
        public final boolean compareAndSet(T obj, long expect, long update) {
            accessCheck(obj);
            return U.compareAndSwapLong(obj, offset, expect, update);
        }

    }
    
    
    
    
    
    
     private static final class LockedUpdater<T> extends AtomicLongFieldUpdater<T> {
     LockedUpdater(final Class<T> tclass, final String fieldName,
                      final Class<?> caller) {
            Field field = null;
            int modifiers = 0;
            try {
                field = AccessController.doPrivileged(
                    new PrivilegedExceptionAction<Field>() {
                        public Field run() throws NoSuchFieldException {
                            return tclass.getDeclaredField(fieldName);
                        }
                    });
                modifiers = field.getModifiers();
                sun.reflect.misc.ReflectUtil.ensureMemberAccess(
                    caller, tclass, null, modifiers);
                ClassLoader cl = tclass.getClassLoader();
                ClassLoader ccl = caller.getClassLoader();
                if ((ccl != null) && (ccl != cl) &&
                    ((cl == null) || !isAncestor(cl, ccl))) {
                    sun.reflect.misc.ReflectUtil.checkPackageAccess(tclass);
                }
            } catch (PrivilegedActionException pae) {
                throw new RuntimeException(pae.getException());
            } catch (Exception ex) {
                throw new RuntimeException(ex);
            }

            if (field.getType() != long.class)
                throw new IllegalArgumentException("Must be long type");

            if (!Modifier.isVolatile(modifiers))
                throw new IllegalArgumentException("Must be volatile type");

            // Access to protected field members is restricted to receivers only
            // of the accessing class, or one of its subclasses, and the
            // accessing class must in turn be a subclass (or package sibling)
            // of the protected member's defining class.
            // If the updater refers to a protected field of a declaring class
            // outside the current package, the receiver argument will be
            // narrowed to the type of the accessing class.
            this.cclass = (Modifier.isProtected(modifiers) &&
                           tclass.isAssignableFrom(caller) &&
                           !isSamePackage(tclass, caller))
                          ? caller : tclass;
            this.tclass = tclass;
            this.offset = U.objectFieldOffset(field);
        }
        
         public final boolean compareAndSet(T obj, long expect, long update) {
            accessCheck(obj);
            synchronized (this) {
                long v = U.getLong(obj, offset);
                if (v != expect)
                    return false;
                U.putLong(obj, offset, update);
                return true;
            }
        }
     
     }
     
     

}
AtomicReferenceFieldUpdater
public abstract class AtomicReferenceFieldUpdater<T,V> {
	 @CallerSensitive
    public static <U,W> AtomicReferenceFieldUpdater<U,W> newUpdater(Class<U> tclass,
                                                                    Class<W> vclass,
                                                                    String fieldName) {
        return new AtomicReferenceFieldUpdaterImpl<U,W>
            (tclass, vclass, fieldName, Reflection.getCallerClass());
    }
    
    public abstract boolean compareAndSet(T obj, V expect, V update);

		
		
		  private static final class AtomicReferenceFieldUpdaterImpl<T,V>
        extends AtomicReferenceFieldUpdater<T,V> {
        
        private static final sun.misc.Unsafe U = sun.misc.Unsafe.getUnsafe();
        private final long offset;
        
        private final Class<?> cclass;
        private final Class<T> tclass;
        private final Class<V> vclass;
        
         AtomicReferenceFieldUpdaterImpl(final Class<T> tclass,
                                        final Class<V> vclass,
                                        final String fieldName,
                                        final Class<?> caller) {
            final Field field;
            final Class<?> fieldClass;
            final int modifiers;
            try {
                field = AccessController.doPrivileged(
                    new PrivilegedExceptionAction<Field>() {
                        public Field run() throws NoSuchFieldException {
                            return tclass.getDeclaredField(fieldName);
                        }
                    });
                modifiers = field.getModifiers();
                sun.reflect.misc.ReflectUtil.ensureMemberAccess(
                    caller, tclass, null, modifiers);
                ClassLoader cl = tclass.getClassLoader();
                ClassLoader ccl = caller.getClassLoader();
                if ((ccl != null) && (ccl != cl) &&
                    ((cl == null) || !isAncestor(cl, ccl))) {
                    sun.reflect.misc.ReflectUtil.checkPackageAccess(tclass);
                }
                fieldClass = field.getType();
            } catch (PrivilegedActionException pae) {
                throw new RuntimeException(pae.getException());
            } catch (Exception ex) {
                throw new RuntimeException(ex);
            }

            if (vclass != fieldClass)
                throw new ClassCastException();
            if (vclass.isPrimitive())
                throw new IllegalArgumentException("Must be reference type");

            if (!Modifier.isVolatile(modifiers))
                throw new IllegalArgumentException("Must be volatile type");

            // Access to protected field members is restricted to receivers only
            // of the accessing class, or one of its subclasses, and the
            // accessing class must in turn be a subclass (or package sibling)
            // of the protected member's defining class.
            // If the updater refers to a protected field of a declaring class
            // outside the current package, the receiver argument will be
            // narrowed to the type of the accessing class.
            this.cclass = (Modifier.isProtected(modifiers) &&
                           tclass.isAssignableFrom(caller) &&
                           !isSamePackage(tclass, caller))
                          ? caller : tclass;
            this.tclass = tclass;
            this.vclass = vclass;
            this.offset = U.objectFieldOffset(field);
        }
        
         public final boolean compareAndSet(T obj, V expect, V update) {
            accessCheck(obj);
            valueCheck(update);
            return U.compareAndSwapObject(obj, offset, expect, update);
        }
        }

}

在单个cas + 自旋的操作下会有性能问题,所以采用分治的思想 将一个变量的累加分散到一个cells 数组中进行,随后用过sum 方法进行聚合,返回用户

原子累加器(Atomic 类源码浅析二 )

  • 4
    点赞
  • 9
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值