--- jsr166/src/test/tck/AtomicLongFieldUpdaterTest.java 2014/12/31 19:21:20 1.28 +++ jsr166/src/test/tck/AtomicLongFieldUpdaterTest.java 2015/11/09 07:54:28 1.31 @@ -13,16 +13,67 @@ import junit.framework.TestSuite; public class AtomicLongFieldUpdaterTest extends JSR166TestCase { volatile long x = 0; - int z; + protected volatile long protectedField; + private volatile long privateField; long w; - + float z; public static void main(String[] args) { - junit.textui.TestRunner.run(suite()); + main(suite(), args); } public static Test suite() { return new TestSuite(AtomicLongFieldUpdaterTest.class); } + // for testing subclass access + static class AtomicLongFieldUpdaterTestSubclass extends AtomicLongFieldUpdaterTest { + public void checkPrivateAccess() { + try { + AtomicLongFieldUpdater a = + AtomicLongFieldUpdater.newUpdater + (AtomicLongFieldUpdaterTest.class, "privateField"); + shouldThrow(); + } catch (RuntimeException success) { + assertNotNull(success.getCause()); + } + } + + public void checkCompareAndSetProtectedSub() { + AtomicLongFieldUpdater a; + a = updaterFor("protectedField"); + protectedField = 1; + assertTrue(a.compareAndSet(this, 1, 2)); + assertTrue(a.compareAndSet(this, 2, -4)); + assertEquals(-4, a.get(this)); + assertFalse(a.compareAndSet(this, -5, 7)); + assertEquals(-4, a.get(this)); + assertTrue(a.compareAndSet(this, -4, 7)); + assertEquals(7, a.get(this)); + } + } + + static class UnrelatedClass { + public void checkPackageAccess(AtomicLongFieldUpdaterTest obj) { + obj.x = 72L; + AtomicLongFieldUpdater a = + AtomicLongFieldUpdater.newUpdater + (AtomicLongFieldUpdaterTest.class, "x"); + assertEquals(72L, a.get(obj)); + assertTrue(a.compareAndSet(obj, 72L, 73L)); + assertEquals(73L, a.get(obj)); + } + + public void checkPrivateAccess(AtomicLongFieldUpdaterTest obj) { + try { + AtomicLongFieldUpdater a = + AtomicLongFieldUpdater.newUpdater + (AtomicLongFieldUpdaterTest.class, "privateField"); + throw new AssertionError("should throw"); + } catch (RuntimeException success) { + assertNotNull(success.getCause()); + } + } + } + AtomicLongFieldUpdater updaterFor(String fieldName) { return AtomicLongFieldUpdater.newUpdater (AtomicLongFieldUpdaterTest.class, fieldName); @@ -61,6 +112,24 @@ public class AtomicLongFieldUpdaterTest } /** + * construction using private field from subclass throws RuntimeException + */ + public void testPrivateFieldInSubclass() { + AtomicLongFieldUpdaterTestSubclass s = + new AtomicLongFieldUpdaterTestSubclass(); + s.checkPrivateAccess(); + } + + /** + * construction from unrelated class; package access is allowed, + * private access is not + */ + public void testUnrelatedClassAccess() { + new UnrelatedClass().checkPackageAccess(this); + new UnrelatedClass().checkPrivateAccess(this); + } + + /** * get returns the last value set or assigned */ public void testGetSet() { @@ -105,6 +174,33 @@ public class AtomicLongFieldUpdaterTest } /** + * compareAndSet succeeds in changing protected field value if + * equal to expected else fails + */ + public void testCompareAndSetProtected() { + AtomicLongFieldUpdater a; + a = updaterFor("protectedField"); + protectedField = 1; + assertTrue(a.compareAndSet(this, 1, 2)); + assertTrue(a.compareAndSet(this, 2, -4)); + assertEquals(-4, a.get(this)); + assertFalse(a.compareAndSet(this, -5, 7)); + assertEquals(-4, a.get(this)); + assertTrue(a.compareAndSet(this, -4, 7)); + assertEquals(7, a.get(this)); + } + + /** + * compareAndSet succeeds in changing protected field value if + * equal to expected else fails + */ + public void testCompareAndSetProtectedInSubclass() { + AtomicLongFieldUpdaterTestSubclass s = + new AtomicLongFieldUpdaterTestSubclass(); + s.checkCompareAndSetProtectedSub(); + } + + /** * compareAndSet in one thread enables another waiting for value * to succeed */