diff --git a/src/java.base/share/classes/java/lang/invoke/MethodHandles.java b/src/java.base/share/classes/java/lang/invoke/MethodHandles.java index 0708ceef3da..530df86bdd6 100644 --- a/src/java.base/share/classes/java/lang/invoke/MethodHandles.java +++ b/src/java.base/share/classes/java/lang/invoke/MethodHandles.java @@ -4513,48 +4513,18 @@ return mh1; * or greater than the {@code byte[]} array length minus the size (in bytes) * of {@code T}. *

- * Access of bytes at an index may be aligned or misaligned for {@code T}, - * with respect to the underlying memory address, {@code A} say, associated - * with the array and index. - * If access is misaligned then access for anything other than the - * {@code get} and {@code set} access modes will result in an - * {@code IllegalStateException}. In such cases atomic access is only - * guaranteed with respect to the largest power of two that divides the GCD - * of {@code A} and the size (in bytes) of {@code T}. - * If access is aligned then following access modes are supported and are - * guaranteed to support atomic access: - *

- *

- * Misaligned access, and therefore atomicity guarantees, may be determined - * for {@code byte[]} arrays without operating on a specific array. Given - * an {@code index}, {@code T} and its corresponding boxed type, - * {@code T_BOX}, misalignment may be determined as follows: - *

{@code
-     * int sizeOfT = T_BOX.BYTES;  // size in bytes of T
-     * int misalignedAtZeroIndex = ByteBuffer.wrap(new byte[0]).
-     *     alignmentOffset(0, sizeOfT);
-     * int misalignedAtIndex = (misalignedAtZeroIndex + index) % sizeOfT;
-     * boolean isMisaligned = misalignedAtIndex != 0;
-     * }
- *

- * If the variable type is {@code float} or {@code double} then atomic - * update access modes compare values using their bitwise representation - * (see {@link Float#floatToRawIntBits} and - * {@link Double#doubleToRawLongBits}, respectively). + * Only plain {@linkplain VarHandle.AccessMode#GET get} and {@linkplain VarHandle.AccessMode#SET set} + * access modes are supported by the returned var handle. For all other access modes, an + * {@link UnsupportedOperationException} will be thrown. + * + * @apiNote if access modes other than plain access are required, clients should + * consider using off-heap memory through + * {@linkplain java.nio.ByteBuffer#allocateDirect(int) direct byte buffers} or + * off-heap {@linkplain java.lang.foreign.MemorySegment memory segments}, + * or memory segments backed by a + * {@linkplain java.lang.foreign.MemorySegment#ofArray(long[]) {@code long[]}}, + * for which stronger alignment guarantees can be made. + * * @param viewArrayClass the view array class, with a component type of * type {@code T} * @param byteOrder the endianness of the view array elements, as @@ -4600,7 +4570,13 @@ return mh1; * or greater than the {@code ByteBuffer} limit minus the size (in bytes) of * {@code T}. *

- * Access of bytes at an index may be aligned or misaligned for {@code T}, + * For heap byte buffers, access is always unaligned. As a result, only the plain + * {@linkplain VarHandle.AccessMode#GET get} + * and {@linkplain VarHandle.AccessMode#SET set} access modes are supported by the + * returned var handle. For all other access modes, an {@link IllegalStateException} + * will be thrown. + *

+ * For direct buffers only, access of bytes at an index may be aligned or misaligned for {@code T}, * with respect to the underlying memory address, {@code A} say, associated * with the {@code ByteBuffer} and index. * If access is misaligned then access for anything other than the diff --git a/src/java.base/share/classes/java/lang/invoke/X-VarHandleByteArrayView.java.template b/src/java.base/share/classes/java/lang/invoke/X-VarHandleByteArrayView.java.template index 08495f2e58d..995cb38e3ca 100644 --- a/src/java.base/share/classes/java/lang/invoke/X-VarHandleByteArrayView.java.template +++ b/src/java.base/share/classes/java/lang/invoke/X-VarHandleByteArrayView.java.template @@ -49,7 +49,7 @@ final class VarHandleByteArrayAs$Type$s extends VarHandleByteArrayBase { static final JavaNioAccess NIO_ACCESS = SharedSecrets.getJavaNioAccess(); static final int ALIGN = $BoxType$.BYTES - 1; - + static final ScopedMemoryAccess SCOPED_MEMORY_ACCESS = ScopedMemoryAccess.getScopedMemoryAccess(); #if[floatingPoint] @@ -115,14 +115,6 @@ final class VarHandleByteArrayAs$Type$s extends VarHandleByteArrayBase { return Preconditions.checkIndex(index, ba.length - ALIGN, Preconditions.AIOOBE_FORMATTER); } - @ForceInline - static long address(byte[] ba, int index) { - long address = ((long) index) + Unsafe.ARRAY_BYTE_BASE_OFFSET; - if ((address & ALIGN) != 0) - throw newIllegalStateExceptionForMisalignedAccess(index); - return address; - } - @ForceInline static $type$ get(VarHandle ob, Object oba, int index) { ArrayHandle handle = (ArrayHandle)ob; @@ -160,419 +152,6 @@ final class VarHandleByteArrayAs$Type$s extends VarHandleByteArrayBase { #end[floatingPoint] } - @ForceInline - static $type$ getVolatile(VarHandle ob, Object oba, int index) { - ArrayHandle handle = (ArrayHandle)ob; - byte[] ba = (byte[]) oba; - return convEndian(handle.be, - UNSAFE.get$RawType$Volatile( - ba, - address(ba, index(ba, index)))); - } - - @ForceInline - static void setVolatile(VarHandle ob, Object oba, int index, $type$ value) { - ArrayHandle handle = (ArrayHandle)ob; - byte[] ba = (byte[]) oba; - UNSAFE.put$RawType$Volatile( - ba, - address(ba, index(ba, index)), - convEndian(handle.be, value)); - } - - @ForceInline - static $type$ getAcquire(VarHandle ob, Object oba, int index) { - ArrayHandle handle = (ArrayHandle)ob; - byte[] ba = (byte[]) oba; - return convEndian(handle.be, - UNSAFE.get$RawType$Acquire( - ba, - address(ba, index(ba, index)))); - } - - @ForceInline - static void setRelease(VarHandle ob, Object oba, int index, $type$ value) { - ArrayHandle handle = (ArrayHandle)ob; - byte[] ba = (byte[]) oba; - UNSAFE.put$RawType$Release( - ba, - address(ba, index(ba, index)), - convEndian(handle.be, value)); - } - - @ForceInline - static $type$ getOpaque(VarHandle ob, Object oba, int index) { - ArrayHandle handle = (ArrayHandle)ob; - byte[] ba = (byte[]) oba; - return convEndian(handle.be, - UNSAFE.get$RawType$Opaque( - ba, - address(ba, index(ba, index)))); - } - - @ForceInline - static void setOpaque(VarHandle ob, Object oba, int index, $type$ value) { - ArrayHandle handle = (ArrayHandle)ob; - byte[] ba = (byte[]) oba; - UNSAFE.put$RawType$Opaque( - ba, - address(ba, index(ba, index)), - convEndian(handle.be, value)); - } -#if[CAS] - - @ForceInline - static boolean compareAndSet(VarHandle ob, Object oba, int index, $type$ expected, $type$ value) { - ArrayHandle handle = (ArrayHandle)ob; - byte[] ba = (byte[]) oba; -#if[Object] - return UNSAFE.compareAndSetReference( - ba, - address(ba, index(ba, index)), - convEndian(handle.be, expected), convEndian(handle.be, value)); -#else[Object] - return UNSAFE.compareAndSet$RawType$( - ba, - address(ba, index(ba, index)), - convEndian(handle.be, expected), convEndian(handle.be, value)); -#end[Object] - } - - @ForceInline - static $type$ compareAndExchange(VarHandle ob, Object oba, int index, $type$ expected, $type$ value) { - ArrayHandle handle = (ArrayHandle)ob; - byte[] ba = (byte[]) oba; - return convEndian(handle.be, - UNSAFE.compareAndExchange$RawType$( - ba, - address(ba, index(ba, index)), - convEndian(handle.be, expected), convEndian(handle.be, value))); - } - - @ForceInline - static $type$ compareAndExchangeAcquire(VarHandle ob, Object oba, int index, $type$ expected, $type$ value) { - ArrayHandle handle = (ArrayHandle)ob; - byte[] ba = (byte[]) oba; - return convEndian(handle.be, - UNSAFE.compareAndExchange$RawType$Acquire( - ba, - address(ba, index(ba, index)), - convEndian(handle.be, expected), convEndian(handle.be, value))); - } - - @ForceInline - static $type$ compareAndExchangeRelease(VarHandle ob, Object oba, int index, $type$ expected, $type$ value) { - ArrayHandle handle = (ArrayHandle)ob; - byte[] ba = (byte[]) oba; - return convEndian(handle.be, - UNSAFE.compareAndExchange$RawType$Release( - ba, - address(ba, index(ba, index)), - convEndian(handle.be, expected), convEndian(handle.be, value))); - } - - @ForceInline - static boolean weakCompareAndSetPlain(VarHandle ob, Object oba, int index, $type$ expected, $type$ value) { - ArrayHandle handle = (ArrayHandle)ob; - byte[] ba = (byte[]) oba; - return UNSAFE.weakCompareAndSet$RawType$Plain( - ba, - address(ba, index(ba, index)), - convEndian(handle.be, expected), convEndian(handle.be, value)); - } - - @ForceInline - static boolean weakCompareAndSet(VarHandle ob, Object oba, int index, $type$ expected, $type$ value) { - ArrayHandle handle = (ArrayHandle)ob; - byte[] ba = (byte[]) oba; - return UNSAFE.weakCompareAndSet$RawType$( - ba, - address(ba, index(ba, index)), - convEndian(handle.be, expected), convEndian(handle.be, value)); - } - - @ForceInline - static boolean weakCompareAndSetAcquire(VarHandle ob, Object oba, int index, $type$ expected, $type$ value) { - ArrayHandle handle = (ArrayHandle)ob; - byte[] ba = (byte[]) oba; - return UNSAFE.weakCompareAndSet$RawType$Acquire( - ba, - address(ba, index(ba, index)), - convEndian(handle.be, expected), convEndian(handle.be, value)); - } - - @ForceInline - static boolean weakCompareAndSetRelease(VarHandle ob, Object oba, int index, $type$ expected, $type$ value) { - ArrayHandle handle = (ArrayHandle)ob; - byte[] ba = (byte[]) oba; - return UNSAFE.weakCompareAndSet$RawType$Release( - ba, - address(ba, index(ba, index)), - convEndian(handle.be, expected), convEndian(handle.be, value)); - } - - @ForceInline - static $type$ getAndSet(VarHandle ob, Object oba, int index, $type$ value) { - ArrayHandle handle = (ArrayHandle)ob; - byte[] ba = (byte[]) oba; -#if[Object] - return convEndian(handle.be, - UNSAFE.getAndSetReference( - ba, - address(ba, index(ba, index)), - convEndian(handle.be, value))); -#else[Object] - return convEndian(handle.be, - UNSAFE.getAndSet$RawType$( - ba, - address(ba, index(ba, index)), - convEndian(handle.be, value))); -#end[Object] - } - - @ForceInline - static $type$ getAndSetAcquire(VarHandle ob, Object oba, int index, $type$ value) { - ArrayHandle handle = (ArrayHandle)ob; - byte[] ba = (byte[]) oba; - return convEndian(handle.be, - UNSAFE.getAndSet$RawType$Acquire( - ba, - address(ba, index(ba, index)), - convEndian(handle.be, value))); - } - - @ForceInline - static $type$ getAndSetRelease(VarHandle ob, Object oba, int index, $type$ value) { - ArrayHandle handle = (ArrayHandle)ob; - byte[] ba = (byte[]) oba; - return convEndian(handle.be, - UNSAFE.getAndSet$RawType$Release( - ba, - address(ba, index(ba, index)), - convEndian(handle.be, value))); - } -#end[CAS] -#if[AtomicAdd] - - @ForceInline - static $type$ getAndAdd(VarHandle ob, Object oba, int index, $type$ delta) { - ArrayHandle handle = (ArrayHandle)ob; - byte[] ba = (byte[]) oba; - if (handle.be == BE) { - return UNSAFE.getAndAdd$RawType$( - ba, - address(ba, index(ba, index)), - delta); - } else { - return getAndAddConvEndianWithCAS(ba, index, delta); - } - } - - @ForceInline - static $type$ getAndAddAcquire(VarHandle ob, Object oba, int index, $type$ delta) { - ArrayHandle handle = (ArrayHandle)ob; - byte[] ba = (byte[]) oba; - if (handle.be == BE) { - return UNSAFE.getAndAdd$RawType$Acquire( - ba, - address(ba, index(ba, index)), - delta); - } else { - return getAndAddConvEndianWithCAS(ba, index, delta); - } - } - - @ForceInline - static $type$ getAndAddRelease(VarHandle ob, Object oba, int index, $type$ delta) { - ArrayHandle handle = (ArrayHandle)ob; - byte[] ba = (byte[]) oba; - if (handle.be == BE) { - return UNSAFE.getAndAdd$RawType$Release( - ba, - address(ba, index(ba, index)), - delta); - } else { - return getAndAddConvEndianWithCAS(ba, index, delta); - } - } - - @ForceInline - static $type$ getAndAddConvEndianWithCAS(byte[] ba, int index, $type$ delta) { - $type$ nativeExpectedValue, expectedValue; - long offset = address(ba, index(ba, index)); - do { - nativeExpectedValue = UNSAFE.get$RawType$Volatile(ba, offset); - expectedValue = $RawBoxType$.reverseBytes(nativeExpectedValue); - } while (!UNSAFE.weakCompareAndSet$RawType$(ba, offset, - nativeExpectedValue, $RawBoxType$.reverseBytes(expectedValue + delta))); - return expectedValue; - } -#end[AtomicAdd] -#if[Bitwise] - - @ForceInline - static $type$ getAndBitwiseOr(VarHandle ob, Object oba, int index, $type$ value) { - ArrayHandle handle = (ArrayHandle)ob; - byte[] ba = (byte[]) oba; - if (handle.be == BE) { - return UNSAFE.getAndBitwiseOr$RawType$( - ba, - address(ba, index(ba, index)), - value); - } else { - return getAndBitwiseOrConvEndianWithCAS(ba, index, value); - } - } - - @ForceInline - static $type$ getAndBitwiseOrRelease(VarHandle ob, Object oba, int index, $type$ value) { - ArrayHandle handle = (ArrayHandle)ob; - byte[] ba = (byte[]) oba; - if (handle.be == BE) { - return UNSAFE.getAndBitwiseOr$RawType$Release( - ba, - address(ba, index(ba, index)), - value); - } else { - return getAndBitwiseOrConvEndianWithCAS(ba, index, value); - } - } - - @ForceInline - static $type$ getAndBitwiseOrAcquire(VarHandle ob, Object oba, int index, $type$ value) { - ArrayHandle handle = (ArrayHandle)ob; - byte[] ba = (byte[]) oba; - if (handle.be == BE) { - return UNSAFE.getAndBitwiseOr$RawType$Acquire( - ba, - address(ba, index(ba, index)), - value); - } else { - return getAndBitwiseOrConvEndianWithCAS(ba, index, value); - } - } - - @ForceInline - static $type$ getAndBitwiseOrConvEndianWithCAS(byte[] ba, int index, $type$ value) { - $type$ nativeExpectedValue, expectedValue; - long offset = address(ba, index(ba, index)); - do { - nativeExpectedValue = UNSAFE.get$RawType$Volatile(ba, offset); - expectedValue = $RawBoxType$.reverseBytes(nativeExpectedValue); - } while (!UNSAFE.weakCompareAndSet$RawType$(ba, offset, - nativeExpectedValue, $RawBoxType$.reverseBytes(expectedValue | value))); - return expectedValue; - } - - @ForceInline - static $type$ getAndBitwiseAnd(VarHandle ob, Object oba, int index, $type$ value) { - ArrayHandle handle = (ArrayHandle)ob; - byte[] ba = (byte[]) oba; - if (handle.be == BE) { - return UNSAFE.getAndBitwiseAnd$RawType$( - ba, - address(ba, index(ba, index)), - value); - } else { - return getAndBitwiseAndConvEndianWithCAS(ba, index, value); - } - } - - @ForceInline - static $type$ getAndBitwiseAndRelease(VarHandle ob, Object oba, int index, $type$ value) { - ArrayHandle handle = (ArrayHandle)ob; - byte[] ba = (byte[]) oba; - if (handle.be == BE) { - return UNSAFE.getAndBitwiseAnd$RawType$Release( - ba, - address(ba, index(ba, index)), - value); - } else { - return getAndBitwiseAndConvEndianWithCAS(ba, index, value); - } - } - - @ForceInline - static $type$ getAndBitwiseAndAcquire(VarHandle ob, Object oba, int index, $type$ value) { - ArrayHandle handle = (ArrayHandle)ob; - byte[] ba = (byte[]) oba; - if (handle.be == BE) { - return UNSAFE.getAndBitwiseAnd$RawType$Acquire( - ba, - address(ba, index(ba, index)), - value); - } else { - return getAndBitwiseAndConvEndianWithCAS(ba, index, value); - } - } - - @ForceInline - static $type$ getAndBitwiseAndConvEndianWithCAS(byte[] ba, int index, $type$ value) { - $type$ nativeExpectedValue, expectedValue; - long offset = address(ba, index(ba, index)); - do { - nativeExpectedValue = UNSAFE.get$RawType$Volatile(ba, offset); - expectedValue = $RawBoxType$.reverseBytes(nativeExpectedValue); - } while (!UNSAFE.weakCompareAndSet$RawType$(ba, offset, - nativeExpectedValue, $RawBoxType$.reverseBytes(expectedValue & value))); - return expectedValue; - } - - @ForceInline - static $type$ getAndBitwiseXor(VarHandle ob, Object oba, int index, $type$ value) { - ArrayHandle handle = (ArrayHandle)ob; - byte[] ba = (byte[]) oba; - if (handle.be == BE) { - return UNSAFE.getAndBitwiseXor$RawType$( - ba, - address(ba, index(ba, index)), - value); - } else { - return getAndBitwiseXorConvEndianWithCAS(ba, index, value); - } - } - - @ForceInline - static $type$ getAndBitwiseXorRelease(VarHandle ob, Object oba, int index, $type$ value) { - ArrayHandle handle = (ArrayHandle)ob; - byte[] ba = (byte[]) oba; - if (handle.be == BE) { - return UNSAFE.getAndBitwiseXor$RawType$Release( - ba, - address(ba, index(ba, index)), - value); - } else { - return getAndBitwiseXorConvEndianWithCAS(ba, index, value); - } - } - - @ForceInline - static $type$ getAndBitwiseXorAcquire(VarHandle ob, Object oba, int index, $type$ value) { - ArrayHandle handle = (ArrayHandle)ob; - byte[] ba = (byte[]) oba; - if (handle.be == BE) { - return UNSAFE.getAndBitwiseXor$RawType$Acquire( - ba, - address(ba, index(ba, index)), - value); - } else { - return getAndBitwiseXorConvEndianWithCAS(ba, index, value); - } - } - - @ForceInline - static $type$ getAndBitwiseXorConvEndianWithCAS(byte[] ba, int index, $type$ value) { - $type$ nativeExpectedValue, expectedValue; - long offset = address(ba, index(ba, index)); - do { - nativeExpectedValue = UNSAFE.get$RawType$Volatile(ba, offset); - expectedValue = $RawBoxType$.reverseBytes(nativeExpectedValue); - } while (!UNSAFE.weakCompareAndSet$RawType$(ba, offset, - nativeExpectedValue, $RawBoxType$.reverseBytes(expectedValue ^ value))); - return expectedValue; - } -#end[Bitwise] - static final VarForm FORM = new VarForm(ArrayHandle.class, byte[].class, $type$.class, int.class); } @@ -634,6 +213,14 @@ final class VarHandleByteArrayAs$Type$s extends VarHandleByteArrayBase { return address; } + @ForceInline + static Object checkNullHeapBase(Object hb) { + if (hb != null) { + throw new IllegalStateException("Atomic access not supported for heap buffer"); + } + return hb; + } + @ForceInline static $type$ get(VarHandle ob, Object obb, int index) { ByteBufferHandle handle = (ByteBufferHandle)ob; @@ -677,7 +264,7 @@ final class VarHandleByteArrayAs$Type$s extends VarHandleByteArrayBase { ByteBuffer bb = (ByteBuffer) Objects.requireNonNull(obb); return convEndian(handle.be, SCOPED_MEMORY_ACCESS.get$RawType$Volatile(session(bb), - UNSAFE.getReference(bb, BYTE_BUFFER_HB), + checkNullHeapBase(UNSAFE.getReference(bb, BYTE_BUFFER_HB)), address(bb, index(bb, index)))); } @@ -686,7 +273,7 @@ final class VarHandleByteArrayAs$Type$s extends VarHandleByteArrayBase { ByteBufferHandle handle = (ByteBufferHandle)ob; ByteBuffer bb = (ByteBuffer) Objects.requireNonNull(obb); SCOPED_MEMORY_ACCESS.put$RawType$Volatile(session(bb), - UNSAFE.getReference(bb, BYTE_BUFFER_HB), + checkNullHeapBase(UNSAFE.getReference(bb, BYTE_BUFFER_HB)), address(bb, indexRO(bb, index)), convEndian(handle.be, value)); } @@ -697,7 +284,7 @@ final class VarHandleByteArrayAs$Type$s extends VarHandleByteArrayBase { ByteBuffer bb = (ByteBuffer) Objects.requireNonNull(obb); return convEndian(handle.be, SCOPED_MEMORY_ACCESS.get$RawType$Acquire(session(bb), - UNSAFE.getReference(bb, BYTE_BUFFER_HB), + checkNullHeapBase(UNSAFE.getReference(bb, BYTE_BUFFER_HB)), address(bb, index(bb, index)))); } @@ -706,7 +293,7 @@ final class VarHandleByteArrayAs$Type$s extends VarHandleByteArrayBase { ByteBufferHandle handle = (ByteBufferHandle)ob; ByteBuffer bb = (ByteBuffer) Objects.requireNonNull(obb); SCOPED_MEMORY_ACCESS.put$RawType$Release(session(bb), - UNSAFE.getReference(bb, BYTE_BUFFER_HB), + checkNullHeapBase(UNSAFE.getReference(bb, BYTE_BUFFER_HB)), address(bb, indexRO(bb, index)), convEndian(handle.be, value)); } @@ -717,7 +304,7 @@ final class VarHandleByteArrayAs$Type$s extends VarHandleByteArrayBase { ByteBuffer bb = (ByteBuffer) Objects.requireNonNull(obb); return convEndian(handle.be, SCOPED_MEMORY_ACCESS.get$RawType$Opaque(session(bb), - UNSAFE.getReference(bb, BYTE_BUFFER_HB), + checkNullHeapBase(UNSAFE.getReference(bb, BYTE_BUFFER_HB)), address(bb, index(bb, index)))); } @@ -726,7 +313,7 @@ final class VarHandleByteArrayAs$Type$s extends VarHandleByteArrayBase { ByteBufferHandle handle = (ByteBufferHandle)ob; ByteBuffer bb = (ByteBuffer) Objects.requireNonNull(obb); SCOPED_MEMORY_ACCESS.put$RawType$Opaque(session(bb), - UNSAFE.getReference(bb, BYTE_BUFFER_HB), + checkNullHeapBase(UNSAFE.getReference(bb, BYTE_BUFFER_HB)), address(bb, indexRO(bb, index)), convEndian(handle.be, value)); } @@ -736,17 +323,10 @@ final class VarHandleByteArrayAs$Type$s extends VarHandleByteArrayBase { static boolean compareAndSet(VarHandle ob, Object obb, int index, $type$ expected, $type$ value) { ByteBufferHandle handle = (ByteBufferHandle)ob; ByteBuffer bb = (ByteBuffer) Objects.requireNonNull(obb); -#if[Object] - return SCOPED_MEMORY_ACCESS.compareAndSetReference(session(bb), - UNSAFE.getReference(bb, BYTE_BUFFER_HB), - address(bb, indexRO(bb, index)), - convEndian(handle.be, expected), convEndian(handle.be, value)); -#else[Object] return SCOPED_MEMORY_ACCESS.compareAndSet$RawType$(session(bb), - UNSAFE.getReference(bb, BYTE_BUFFER_HB), + checkNullHeapBase(UNSAFE.getReference(bb, BYTE_BUFFER_HB)), address(bb, indexRO(bb, index)), convEndian(handle.be, expected), convEndian(handle.be, value)); -#end[Object] } @ForceInline @@ -755,7 +335,7 @@ final class VarHandleByteArrayAs$Type$s extends VarHandleByteArrayBase { ByteBuffer bb = (ByteBuffer) Objects.requireNonNull(obb); return convEndian(handle.be, SCOPED_MEMORY_ACCESS.compareAndExchange$RawType$(session(bb), - UNSAFE.getReference(bb, BYTE_BUFFER_HB), + checkNullHeapBase(UNSAFE.getReference(bb, BYTE_BUFFER_HB)), address(bb, indexRO(bb, index)), convEndian(handle.be, expected), convEndian(handle.be, value))); } @@ -766,7 +346,7 @@ final class VarHandleByteArrayAs$Type$s extends VarHandleByteArrayBase { ByteBuffer bb = (ByteBuffer) Objects.requireNonNull(obb); return convEndian(handle.be, SCOPED_MEMORY_ACCESS.compareAndExchange$RawType$Acquire(session(bb), - UNSAFE.getReference(bb, BYTE_BUFFER_HB), + checkNullHeapBase(UNSAFE.getReference(bb, BYTE_BUFFER_HB)), address(bb, indexRO(bb, index)), convEndian(handle.be, expected), convEndian(handle.be, value))); } @@ -777,7 +357,7 @@ final class VarHandleByteArrayAs$Type$s extends VarHandleByteArrayBase { ByteBuffer bb = (ByteBuffer) Objects.requireNonNull(obb); return convEndian(handle.be, SCOPED_MEMORY_ACCESS.compareAndExchange$RawType$Release(session(bb), - UNSAFE.getReference(bb, BYTE_BUFFER_HB), + checkNullHeapBase(UNSAFE.getReference(bb, BYTE_BUFFER_HB)), address(bb, indexRO(bb, index)), convEndian(handle.be, expected), convEndian(handle.be, value))); } @@ -787,7 +367,7 @@ final class VarHandleByteArrayAs$Type$s extends VarHandleByteArrayBase { ByteBufferHandle handle = (ByteBufferHandle)ob; ByteBuffer bb = (ByteBuffer) Objects.requireNonNull(obb); return SCOPED_MEMORY_ACCESS.weakCompareAndSet$RawType$Plain(session(bb), - UNSAFE.getReference(bb, BYTE_BUFFER_HB), + checkNullHeapBase(UNSAFE.getReference(bb, BYTE_BUFFER_HB)), address(bb, indexRO(bb, index)), convEndian(handle.be, expected), convEndian(handle.be, value)); } @@ -797,7 +377,7 @@ final class VarHandleByteArrayAs$Type$s extends VarHandleByteArrayBase { ByteBufferHandle handle = (ByteBufferHandle)ob; ByteBuffer bb = (ByteBuffer) Objects.requireNonNull(obb); return SCOPED_MEMORY_ACCESS.weakCompareAndSet$RawType$(session(bb), - UNSAFE.getReference(bb, BYTE_BUFFER_HB), + checkNullHeapBase(UNSAFE.getReference(bb, BYTE_BUFFER_HB)), address(bb, indexRO(bb, index)), convEndian(handle.be, expected), convEndian(handle.be, value)); } @@ -807,7 +387,7 @@ final class VarHandleByteArrayAs$Type$s extends VarHandleByteArrayBase { ByteBufferHandle handle = (ByteBufferHandle)ob; ByteBuffer bb = (ByteBuffer) Objects.requireNonNull(obb); return SCOPED_MEMORY_ACCESS.weakCompareAndSet$RawType$Acquire(session(bb), - UNSAFE.getReference(bb, BYTE_BUFFER_HB), + checkNullHeapBase(UNSAFE.getReference(bb, BYTE_BUFFER_HB)), address(bb, indexRO(bb, index)), convEndian(handle.be, expected), convEndian(handle.be, value)); } @@ -817,7 +397,7 @@ final class VarHandleByteArrayAs$Type$s extends VarHandleByteArrayBase { ByteBufferHandle handle = (ByteBufferHandle)ob; ByteBuffer bb = (ByteBuffer) Objects.requireNonNull(obb); return SCOPED_MEMORY_ACCESS.weakCompareAndSet$RawType$Release(session(bb), - UNSAFE.getReference(bb, BYTE_BUFFER_HB), + checkNullHeapBase(UNSAFE.getReference(bb, BYTE_BUFFER_HB)), address(bb, indexRO(bb, index)), convEndian(handle.be, expected), convEndian(handle.be, value)); } @@ -826,19 +406,11 @@ final class VarHandleByteArrayAs$Type$s extends VarHandleByteArrayBase { static $type$ getAndSet(VarHandle ob, Object obb, int index, $type$ value) { ByteBufferHandle handle = (ByteBufferHandle)ob; ByteBuffer bb = (ByteBuffer) Objects.requireNonNull(obb); -#if[Object] - return convEndian(handle.be, - SCOPED_MEMORY_ACCESS.getAndSetReference(session(bb), - UNSAFE.getReference(bb, BYTE_BUFFER_HB), - address(bb, indexRO(bb, index)), - convEndian(handle.be, value))); -#else[Object] return convEndian(handle.be, SCOPED_MEMORY_ACCESS.getAndSet$RawType$(session(bb), - UNSAFE.getReference(bb, BYTE_BUFFER_HB), + checkNullHeapBase(UNSAFE.getReference(bb, BYTE_BUFFER_HB)), address(bb, indexRO(bb, index)), convEndian(handle.be, value))); -#end[Object] } @ForceInline @@ -847,7 +419,7 @@ final class VarHandleByteArrayAs$Type$s extends VarHandleByteArrayBase { ByteBuffer bb = (ByteBuffer) Objects.requireNonNull(obb); return convEndian(handle.be, SCOPED_MEMORY_ACCESS.getAndSet$RawType$Acquire(session(bb), - UNSAFE.getReference(bb, BYTE_BUFFER_HB), + checkNullHeapBase(UNSAFE.getReference(bb, BYTE_BUFFER_HB)), address(bb, indexRO(bb, index)), convEndian(handle.be, value))); } @@ -858,7 +430,7 @@ final class VarHandleByteArrayAs$Type$s extends VarHandleByteArrayBase { ByteBuffer bb = (ByteBuffer) Objects.requireNonNull(obb); return convEndian(handle.be, SCOPED_MEMORY_ACCESS.getAndSet$RawType$Release(session(bb), - UNSAFE.getReference(bb, BYTE_BUFFER_HB), + checkNullHeapBase(UNSAFE.getReference(bb, BYTE_BUFFER_HB)), address(bb, indexRO(bb, index)), convEndian(handle.be, value))); } @@ -871,7 +443,7 @@ final class VarHandleByteArrayAs$Type$s extends VarHandleByteArrayBase { ByteBuffer bb = (ByteBuffer) Objects.requireNonNull(obb); if (handle.be == BE) { return SCOPED_MEMORY_ACCESS.getAndAdd$RawType$(session(bb), - UNSAFE.getReference(bb, BYTE_BUFFER_HB), + checkNullHeapBase(UNSAFE.getReference(bb, BYTE_BUFFER_HB)), address(bb, indexRO(bb, index)), delta); } else { @@ -885,7 +457,7 @@ final class VarHandleByteArrayAs$Type$s extends VarHandleByteArrayBase { ByteBuffer bb = (ByteBuffer) Objects.requireNonNull(obb); if (handle.be == BE) { return SCOPED_MEMORY_ACCESS.getAndAdd$RawType$Acquire(session(bb), - UNSAFE.getReference(bb, BYTE_BUFFER_HB), + checkNullHeapBase(UNSAFE.getReference(bb, BYTE_BUFFER_HB)), address(bb, indexRO(bb, index)), delta); } else { @@ -899,7 +471,7 @@ final class VarHandleByteArrayAs$Type$s extends VarHandleByteArrayBase { ByteBuffer bb = (ByteBuffer) Objects.requireNonNull(obb); if (handle.be == BE) { return SCOPED_MEMORY_ACCESS.getAndAdd$RawType$Release(session(bb), - UNSAFE.getReference(bb, BYTE_BUFFER_HB), + checkNullHeapBase(UNSAFE.getReference(bb, BYTE_BUFFER_HB)), address(bb, indexRO(bb, index)), delta); } else { @@ -910,7 +482,7 @@ final class VarHandleByteArrayAs$Type$s extends VarHandleByteArrayBase { @ForceInline static $type$ getAndAddConvEndianWithCAS(ByteBuffer bb, int index, $type$ delta) { $type$ nativeExpectedValue, expectedValue; - Object base = UNSAFE.getReference(bb, BYTE_BUFFER_HB); + Object base = checkNullHeapBase(UNSAFE.getReference(bb, BYTE_BUFFER_HB)); long offset = address(bb, indexRO(bb, index)); do { nativeExpectedValue = SCOPED_MEMORY_ACCESS.get$RawType$Volatile(session(bb), base, offset); @@ -928,7 +500,7 @@ final class VarHandleByteArrayAs$Type$s extends VarHandleByteArrayBase { ByteBuffer bb = (ByteBuffer) Objects.requireNonNull(obb); if (handle.be == BE) { return SCOPED_MEMORY_ACCESS.getAndBitwiseOr$RawType$(session(bb), - UNSAFE.getReference(bb, BYTE_BUFFER_HB), + checkNullHeapBase(UNSAFE.getReference(bb, BYTE_BUFFER_HB)), address(bb, indexRO(bb, index)), value); } else { @@ -942,7 +514,7 @@ final class VarHandleByteArrayAs$Type$s extends VarHandleByteArrayBase { ByteBuffer bb = (ByteBuffer) Objects.requireNonNull(obb); if (handle.be == BE) { return SCOPED_MEMORY_ACCESS.getAndBitwiseOr$RawType$Release(session(bb), - UNSAFE.getReference(bb, BYTE_BUFFER_HB), + checkNullHeapBase(UNSAFE.getReference(bb, BYTE_BUFFER_HB)), address(bb, indexRO(bb, index)), value); } else { @@ -956,7 +528,7 @@ final class VarHandleByteArrayAs$Type$s extends VarHandleByteArrayBase { ByteBuffer bb = (ByteBuffer) Objects.requireNonNull(obb); if (handle.be == BE) { return SCOPED_MEMORY_ACCESS.getAndBitwiseOr$RawType$Acquire(session(bb), - UNSAFE.getReference(bb, BYTE_BUFFER_HB), + checkNullHeapBase(UNSAFE.getReference(bb, BYTE_BUFFER_HB)), address(bb, indexRO(bb, index)), value); } else { @@ -967,7 +539,7 @@ final class VarHandleByteArrayAs$Type$s extends VarHandleByteArrayBase { @ForceInline static $type$ getAndBitwiseOrConvEndianWithCAS(ByteBuffer bb, int index, $type$ value) { $type$ nativeExpectedValue, expectedValue; - Object base = UNSAFE.getReference(bb, BYTE_BUFFER_HB); + Object base = checkNullHeapBase(UNSAFE.getReference(bb, BYTE_BUFFER_HB)); long offset = address(bb, indexRO(bb, index)); do { nativeExpectedValue = SCOPED_MEMORY_ACCESS.get$RawType$Volatile(session(bb), base, offset); @@ -983,7 +555,7 @@ final class VarHandleByteArrayAs$Type$s extends VarHandleByteArrayBase { ByteBuffer bb = (ByteBuffer) Objects.requireNonNull(obb); if (handle.be == BE) { return SCOPED_MEMORY_ACCESS.getAndBitwiseAnd$RawType$(session(bb), - UNSAFE.getReference(bb, BYTE_BUFFER_HB), + checkNullHeapBase(UNSAFE.getReference(bb, BYTE_BUFFER_HB)), address(bb, indexRO(bb, index)), value); } else { @@ -997,7 +569,7 @@ final class VarHandleByteArrayAs$Type$s extends VarHandleByteArrayBase { ByteBuffer bb = (ByteBuffer) Objects.requireNonNull(obb); if (handle.be == BE) { return SCOPED_MEMORY_ACCESS.getAndBitwiseAnd$RawType$Release(session(bb), - UNSAFE.getReference(bb, BYTE_BUFFER_HB), + checkNullHeapBase(UNSAFE.getReference(bb, BYTE_BUFFER_HB)), address(bb, indexRO(bb, index)), value); } else { @@ -1011,7 +583,7 @@ final class VarHandleByteArrayAs$Type$s extends VarHandleByteArrayBase { ByteBuffer bb = (ByteBuffer) Objects.requireNonNull(obb); if (handle.be == BE) { return SCOPED_MEMORY_ACCESS.getAndBitwiseAnd$RawType$Acquire(session(bb), - UNSAFE.getReference(bb, BYTE_BUFFER_HB), + checkNullHeapBase(UNSAFE.getReference(bb, BYTE_BUFFER_HB)), address(bb, indexRO(bb, index)), value); } else { @@ -1022,7 +594,7 @@ final class VarHandleByteArrayAs$Type$s extends VarHandleByteArrayBase { @ForceInline static $type$ getAndBitwiseAndConvEndianWithCAS(ByteBuffer bb, int index, $type$ value) { $type$ nativeExpectedValue, expectedValue; - Object base = UNSAFE.getReference(bb, BYTE_BUFFER_HB); + Object base = checkNullHeapBase(UNSAFE.getReference(bb, BYTE_BUFFER_HB)); long offset = address(bb, indexRO(bb, index)); do { nativeExpectedValue = SCOPED_MEMORY_ACCESS.get$RawType$Volatile(session(bb), base, offset); @@ -1039,7 +611,7 @@ final class VarHandleByteArrayAs$Type$s extends VarHandleByteArrayBase { ByteBuffer bb = (ByteBuffer) Objects.requireNonNull(obb); if (handle.be == BE) { return SCOPED_MEMORY_ACCESS.getAndBitwiseXor$RawType$(session(bb), - UNSAFE.getReference(bb, BYTE_BUFFER_HB), + checkNullHeapBase(UNSAFE.getReference(bb, BYTE_BUFFER_HB)), address(bb, indexRO(bb, index)), value); } else { @@ -1053,7 +625,7 @@ final class VarHandleByteArrayAs$Type$s extends VarHandleByteArrayBase { ByteBuffer bb = (ByteBuffer) Objects.requireNonNull(obb); if (handle.be == BE) { return SCOPED_MEMORY_ACCESS.getAndBitwiseXor$RawType$Release(session(bb), - UNSAFE.getReference(bb, BYTE_BUFFER_HB), + checkNullHeapBase(UNSAFE.getReference(bb, BYTE_BUFFER_HB)), address(bb, indexRO(bb, index)), value); } else { @@ -1067,7 +639,7 @@ final class VarHandleByteArrayAs$Type$s extends VarHandleByteArrayBase { ByteBuffer bb = (ByteBuffer) Objects.requireNonNull(obb); if (handle.be == BE) { return SCOPED_MEMORY_ACCESS.getAndBitwiseXor$RawType$Acquire(session(bb), - UNSAFE.getReference(bb, BYTE_BUFFER_HB), + checkNullHeapBase(UNSAFE.getReference(bb, BYTE_BUFFER_HB)), address(bb, indexRO(bb, index)), value); } else { @@ -1078,7 +650,7 @@ final class VarHandleByteArrayAs$Type$s extends VarHandleByteArrayBase { @ForceInline static $type$ getAndBitwiseXorConvEndianWithCAS(ByteBuffer bb, int index, $type$ value) { $type$ nativeExpectedValue, expectedValue; - Object base = UNSAFE.getReference(bb, BYTE_BUFFER_HB); + Object base = checkNullHeapBase(UNSAFE.getReference(bb, BYTE_BUFFER_HB)); long offset = address(bb, indexRO(bb, index)); do { nativeExpectedValue = SCOPED_MEMORY_ACCESS.get$RawType$Volatile(session(bb), base, offset); diff --git a/src/java.base/share/classes/java/nio/X-Buffer.java.template b/src/java.base/share/classes/java/nio/X-Buffer.java.template index 2146c86a577..1b378a2ef4a 100644 --- a/src/java.base/share/classes/java/nio/X-Buffer.java.template +++ b/src/java.base/share/classes/java/nio/X-Buffer.java.template @@ -1557,7 +1557,7 @@ public abstract sealed class $Type$Buffer super.position(newPosition); return this; } - + /** * {@inheritDoc} * @since 9 @@ -1571,13 +1571,13 @@ public abstract sealed class $Type$Buffer super.limit(newLimit); return this; } - + /** * {@inheritDoc} * @since 9 */ @Override - public + public #if[!byte] final #end[!byte] @@ -1591,7 +1591,7 @@ public abstract sealed class $Type$Buffer * @since 9 */ @Override - public + public #if[!byte] final #end[!byte] @@ -1605,7 +1605,7 @@ public abstract sealed class $Type$Buffer * @since 9 */ @Override - public + public #if[!byte] final #end[!byte] @@ -1619,7 +1619,7 @@ public abstract sealed class $Type$Buffer * @since 9 */ @Override - public + public #if[!byte] final #end[!byte] @@ -1633,7 +1633,7 @@ public abstract sealed class $Type$Buffer * @since 9 */ @Override - public + public #if[!byte] final #end[!byte] @@ -2208,15 +2208,11 @@ public abstract sealed class $Type$Buffer * alignmentOffset(index + (unitSize - value), unitSize) == 0 * } * must hold. - * + * * @apiNote * This method may be utilized to determine if unit size bytes from an * index can be accessed atomically, if supported by the native platform. * - * @implNote - * This implementation throws {@code UnsupportedOperationException} for - * non-direct buffers when the given unit size is greater then {@code 8}. - * * @param index * The index to query for alignment offset, must be non-negative, no * upper bounds check is performed @@ -2231,13 +2227,7 @@ public abstract sealed class $Type$Buffer * {@code 2} * * @throws UnsupportedOperationException - * If the native platform does not guarantee stable alignment offset - * values for the given unit size when managing the memory regions - * of buffers of the same kind as this buffer (direct or - * non-direct). For example, if garbage collection would result - * in the moving of a memory region covered by a non-direct buffer - * from one location to another and both locations have different - * alignment characteristics. + * If the buffer is non-direct, and {@code unitSize > 1} * * @see #alignedSlice(int) * @since 9 @@ -2247,7 +2237,7 @@ public abstract sealed class $Type$Buffer throw new IllegalArgumentException("Index less than zero: " + index); if (unitSize < 1 || (unitSize & (unitSize - 1)) != 0) throw new IllegalArgumentException("Unit size not a power of two: " + unitSize); - if (unitSize > 8 && !isDirect()) + if (unitSize > 1 && !isDirect()) throw new UnsupportedOperationException("Unit size unsupported for non-direct buffers: " + unitSize); return (int) ((address + index) & (unitSize - 1)); @@ -2287,10 +2277,6 @@ public abstract sealed class $Type$Buffer * from index, that is a multiple of the unit size, may be accessed * atomically, if supported by the native platform. * - * @implNote - * This implementation throws {@code UnsupportedOperationException} for - * non-direct buffers when the given unit size is greater then {@code 8}. - * * @param unitSize * The unit size in bytes, must be a power of {@code 2} * @@ -2300,13 +2286,7 @@ public abstract sealed class $Type$Buffer * If the unit size not a power of {@code 2} * * @throws UnsupportedOperationException - * If the native platform does not guarantee stable aligned slices - * for the given unit size when managing the memory regions - * of buffers of the same kind as this buffer (direct or - * non-direct). For example, if garbage collection would result - * in the moving of a memory region covered by a non-direct buffer - * from one location to another and both locations have different - * alignment characteristics. + * If the buffer is non-direct, and {@code unitSize > 1} * * @see #alignmentOffset(int, int) * @see #slice() diff --git a/test/jdk/java/lang/invoke/VarHandles/VarHandleBaseByteArrayTest.java b/test/jdk/java/lang/invoke/VarHandles/VarHandleBaseByteArrayTest.java index 9d74f2da26e..f88bb052f5e 100644 --- a/test/jdk/java/lang/invoke/VarHandles/VarHandleBaseByteArrayTest.java +++ b/test/jdk/java/lang/invoke/VarHandles/VarHandleBaseByteArrayTest.java @@ -159,8 +159,11 @@ public abstract class VarHandleBaseByteArrayTest extends VarHandleBaseTest { } static class VarHandleSource extends Source { - VarHandleSource(VarHandle vh, MemoryMode... modes) { + final boolean supportsAtomicAccess; + + VarHandleSource(VarHandle vh, boolean supportsAtomicAccess, MemoryMode... modes) { super(vh, modes); + this.supportsAtomicAccess = supportsAtomicAccess; } boolean matches(ByteArrayViewSource bav) { diff --git a/test/jdk/java/lang/invoke/VarHandles/VarHandleTestByteArrayAsChar.java b/test/jdk/java/lang/invoke/VarHandles/VarHandleTestByteArrayAsChar.java index ea2aca9b543..b18655fcb03 100644 --- a/test/jdk/java/lang/invoke/VarHandles/VarHandleTestByteArrayAsChar.java +++ b/test/jdk/java/lang/invoke/VarHandles/VarHandleTestByteArrayAsChar.java @@ -72,12 +72,12 @@ public class VarHandleTestByteArrayAsChar extends VarHandleBaseByteArrayTest { arrayType = int[].class; } VarHandleSource aeh = new VarHandleSource( - MethodHandles.byteArrayViewVarHandle(arrayType, bo), + MethodHandles.byteArrayViewVarHandle(arrayType, bo), false, endianess, MemoryMode.READ_WRITE); vhss.add(aeh); VarHandleSource bbh = new VarHandleSource( - MethodHandles.byteBufferViewVarHandle(arrayType, bo), + MethodHandles.byteBufferViewVarHandle(arrayType, bo), true, endianess, MemoryMode.READ_WRITE); vhss.add(bbh); } @@ -114,38 +114,48 @@ public class VarHandleTestByteArrayAsChar extends VarHandleBaseByteArrayTest { assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET)); assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_VOLATILE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_VOLATILE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_ACQUIRE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_RELEASE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_OPAQUE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_OPAQUE)); + if (vhs.supportsAtomicAccess) { + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_VOLATILE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_VOLATILE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_ACQUIRE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_RELEASE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_OPAQUE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_OPAQUE)); + } else { + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_VOLATILE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.SET_VOLATILE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.SET_RELEASE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_OPAQUE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.SET_OPAQUE)); + } - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_SET)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_ACQUIRE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_RELEASE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_PLAIN)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_ACQUIRE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_RELEASE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET_ACQUIRE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET_RELEASE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_SET)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_RELEASE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_PLAIN)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_RELEASE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET_RELEASE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD_ACQUIRE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD_RELEASE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD_RELEASE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR_ACQUIRE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR_RELEASE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND_ACQUIRE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND_RELEASE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR_ACQUIRE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR_RELEASE)); + + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR_RELEASE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND_RELEASE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR_RELEASE)); } @Test(dataProvider = "typesProvider") @@ -180,9 +190,6 @@ public class VarHandleTestByteArrayAsChar extends VarHandleBaseByteArrayTest { cases.add(new VarHandleSourceAccessTestCase( "index out of bounds", bav, vh, h -> testArrayIndexOutOfBounds(bas, h), false)); - cases.add(new VarHandleSourceAccessTestCase( - "misaligned access", bav, vh, h -> testArrayMisalignedAccess(bas, h), - false)); } else { ByteBufferSource bbs = (ByteBufferSource) bav; @@ -207,9 +214,11 @@ public class VarHandleTestByteArrayAsChar extends VarHandleBaseByteArrayTest { cases.add(new VarHandleSourceAccessTestCase( "index out of bounds", bav, vh, h -> testArrayIndexOutOfBounds(bbs, h), false)); - cases.add(new VarHandleSourceAccessTestCase( - "misaligned access", bav, vh, h -> testArrayMisalignedAccess(bbs, h), - false)); + if (bbs.s.isDirect()) { + cases.add(new VarHandleSourceAccessTestCase( + "misaligned access", bav, vh, h -> testArrayMisalignedAccess(bbs, h), + false)); + } } } } @@ -243,33 +252,6 @@ public class VarHandleTestByteArrayAsChar extends VarHandleBaseByteArrayTest { checkNPE(() -> { vh.set(array, ci, VALUE_1); }); - - checkNPE(() -> { - char x = (char) vh.getVolatile(array, ci); - }); - - checkNPE(() -> { - char x = (char) vh.getAcquire(array, ci); - }); - - checkNPE(() -> { - char x = (char) vh.getOpaque(array, ci); - }); - - checkNPE(() -> { - vh.setVolatile(array, ci, VALUE_1); - }); - - checkNPE(() -> { - vh.setRelease(array, ci, VALUE_1); - }); - - checkNPE(() -> { - vh.setOpaque(array, ci, VALUE_1); - }); - - - } static void testArrayNPE(ByteBufferSource bs, VarHandleSource vhs) { @@ -423,7 +405,7 @@ public class VarHandleTestByteArrayAsChar extends VarHandleBaseByteArrayTest { }); } - if (readOnly) { + if (readOnly && array.isDirect()) { checkROBE(() -> { vh.setVolatile(array, ci, VALUE_1); }); @@ -435,6 +417,11 @@ public class VarHandleTestByteArrayAsChar extends VarHandleBaseByteArrayTest { checkROBE(() -> { vh.setOpaque(array, ci, VALUE_1); }); + + + } + + if (array.isDirect()) { checkUOE(() -> { boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); }); @@ -478,7 +465,6 @@ public class VarHandleTestByteArrayAsChar extends VarHandleBaseByteArrayTest { checkUOE(() -> { char o = (char) vh.getAndSetRelease(array, ci, VALUE_1); }); - checkUOE(() -> { char o = (char) vh.getAndAdd(array, ci, VALUE_1); }); @@ -490,7 +476,6 @@ public class VarHandleTestByteArrayAsChar extends VarHandleBaseByteArrayTest { checkUOE(() -> { char o = (char) vh.getAndAddRelease(array, ci, VALUE_1); }); - checkUOE(() -> { char o = (char) vh.getAndBitwiseOr(array, ci, VALUE_1); }); @@ -526,8 +511,18 @@ public class VarHandleTestByteArrayAsChar extends VarHandleBaseByteArrayTest { checkUOE(() -> { char o = (char) vh.getAndBitwiseXorRelease(array, ci, VALUE_1); }); - } - else { + } else { + checkISE(() -> { + vh.setVolatile(array, ci, VALUE_1); + }); + + checkISE(() -> { + vh.setRelease(array, ci, VALUE_1); + }); + + checkISE(() -> { + vh.setOpaque(array, ci, VALUE_1); + }); checkUOE(() -> { boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); }); @@ -636,33 +631,6 @@ public class VarHandleTestByteArrayAsChar extends VarHandleBaseByteArrayTest { checkAIOOBE(() -> { vh.set(array, ci, VALUE_1); }); - - checkAIOOBE(() -> { - char x = (char) vh.getVolatile(array, ci); - }); - - checkAIOOBE(() -> { - char x = (char) vh.getAcquire(array, ci); - }); - - checkAIOOBE(() -> { - char x = (char) vh.getOpaque(array, ci); - }); - - checkAIOOBE(() -> { - vh.setVolatile(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - vh.setRelease(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - vh.setOpaque(array, ci, VALUE_1); - }); - - - } } @@ -686,74 +654,35 @@ public class VarHandleTestByteArrayAsChar extends VarHandleBaseByteArrayTest { }); } - checkIOOBE(() -> { - char x = (char) vh.getVolatile(array, ci); - }); - - checkIOOBE(() -> { - char x = (char) vh.getAcquire(array, ci); - }); - - checkIOOBE(() -> { - char x = (char) vh.getOpaque(array, ci); - }); - - if (!readOnly) { + if (array.isDirect()) { checkIOOBE(() -> { - vh.setVolatile(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - vh.setRelease(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - vh.setOpaque(array, ci, VALUE_1); - }); - - - - } - } - } - - static void testArrayMisalignedAccess(ByteArraySource bs, VarHandleSource vhs) throws Throwable { - VarHandle vh = vhs.s; - byte[] array = bs.s; - - int misalignmentAtZero = ByteBuffer.wrap(array).alignmentOffset(0, SIZE); - - int length = array.length - SIZE + 1; - for (int i = 0; i < length; i++) { - boolean iAligned = ((i + misalignmentAtZero) & (SIZE - 1)) == 0; - final int ci = i; - - if (!iAligned) { - checkISE(() -> { char x = (char) vh.getVolatile(array, ci); }); - checkISE(() -> { + checkIOOBE(() -> { char x = (char) vh.getAcquire(array, ci); }); - checkISE(() -> { + checkIOOBE(() -> { char x = (char) vh.getOpaque(array, ci); }); - checkISE(() -> { - vh.setVolatile(array, ci, VALUE_1); - }); + if (!readOnly) { + checkIOOBE(() -> { + vh.setVolatile(array, ci, VALUE_1); + }); - checkISE(() -> { - vh.setRelease(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + vh.setRelease(array, ci, VALUE_1); + }); - checkISE(() -> { - vh.setOpaque(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + vh.setOpaque(array, ci, VALUE_1); + }); + + } } } } @@ -795,9 +724,6 @@ public class VarHandleTestByteArrayAsChar extends VarHandleBaseByteArrayTest { checkISE(() -> { vh.setOpaque(array, ci, VALUE_1); }); - - - } } } @@ -807,45 +733,15 @@ public class VarHandleTestByteArrayAsChar extends VarHandleBaseByteArrayTest { VarHandle vh = vhs.s; byte[] array = bs.s; - int misalignmentAtZero = ByteBuffer.wrap(array).alignmentOffset(0, SIZE); - bs.fill((byte) 0xff); int length = array.length - SIZE + 1; for (int i = 0; i < length; i++) { - boolean iAligned = ((i + misalignmentAtZero) & (SIZE - 1)) == 0; - // Plain { vh.set(array, i, VALUE_1); char x = (char) vh.get(array, i); assertEquals(x, VALUE_1, "get char value"); } - - - if (iAligned) { - // Volatile - { - vh.setVolatile(array, i, VALUE_2); - char x = (char) vh.getVolatile(array, i); - assertEquals(x, VALUE_2, "setVolatile char value"); - } - - // Lazy - { - vh.setRelease(array, i, VALUE_1); - char x = (char) vh.getAcquire(array, i); - assertEquals(x, VALUE_1, "setRelease char value"); - } - - // Opaque - { - vh.setOpaque(array, i, VALUE_2); - char x = (char) vh.getOpaque(array, i); - assertEquals(x, VALUE_2, "setOpaque char value"); - } - - - } } } @@ -854,12 +750,10 @@ public class VarHandleTestByteArrayAsChar extends VarHandleBaseByteArrayTest { VarHandle vh = vhs.s; ByteBuffer array = bs.s; - int misalignmentAtZero = array.alignmentOffset(0, SIZE); - bs.fill((byte) 0xff); int length = array.limit() - SIZE + 1; for (int i = 0; i < length; i++) { - boolean iAligned = ((i + misalignmentAtZero) & (SIZE - 1)) == 0; + boolean iAligned = array.isDirect() ? ((i + array.alignmentOffset(0, SIZE)) & (SIZE - 1)) == 0 : false; // Plain { @@ -899,15 +793,13 @@ public class VarHandleTestByteArrayAsChar extends VarHandleBaseByteArrayTest { VarHandle vh = vhs.s; ByteBuffer array = bs.s; - int misalignmentAtZero = array.alignmentOffset(0, SIZE); - ByteBuffer bb = ByteBuffer.allocate(SIZE); bb.order(MemoryMode.BIG_ENDIAN.isSet(vhs.memoryModes) ? ByteOrder.BIG_ENDIAN : ByteOrder.LITTLE_ENDIAN); bs.fill(bb.putChar(0, VALUE_2).array()); int length = array.limit() - SIZE + 1; for (int i = 0; i < length; i++) { - boolean iAligned = ((i + misalignmentAtZero) & (SIZE - 1)) == 0; + boolean iAligned = array.isDirect() ? ((i + array.alignmentOffset(0, SIZE)) & (SIZE - 1)) == 0 : false; char v = MemoryMode.BIG_ENDIAN.isSet(vhs.memoryModes) ? rotateLeft(VALUE_2, (i % SIZE) << 3) diff --git a/test/jdk/java/lang/invoke/VarHandles/VarHandleTestByteArrayAsDouble.java b/test/jdk/java/lang/invoke/VarHandles/VarHandleTestByteArrayAsDouble.java index 9dcaf219323..808c3ec04cb 100644 --- a/test/jdk/java/lang/invoke/VarHandles/VarHandleTestByteArrayAsDouble.java +++ b/test/jdk/java/lang/invoke/VarHandles/VarHandleTestByteArrayAsDouble.java @@ -72,12 +72,12 @@ public class VarHandleTestByteArrayAsDouble extends VarHandleBaseByteArrayTest { arrayType = int[].class; } VarHandleSource aeh = new VarHandleSource( - MethodHandles.byteArrayViewVarHandle(arrayType, bo), + MethodHandles.byteArrayViewVarHandle(arrayType, bo), false, endianess, MemoryMode.READ_WRITE); vhss.add(aeh); VarHandleSource bbh = new VarHandleSource( - MethodHandles.byteBufferViewVarHandle(arrayType, bo), + MethodHandles.byteBufferViewVarHandle(arrayType, bo), true, endianess, MemoryMode.READ_WRITE); vhss.add(bbh); } @@ -114,38 +114,62 @@ public class VarHandleTestByteArrayAsDouble extends VarHandleBaseByteArrayTest { assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET)); assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_VOLATILE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_VOLATILE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_ACQUIRE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_RELEASE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_OPAQUE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_OPAQUE)); + if (vhs.supportsAtomicAccess) { + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_VOLATILE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_VOLATILE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_ACQUIRE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_RELEASE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_OPAQUE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_OPAQUE)); + } else { + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_VOLATILE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.SET_VOLATILE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.SET_RELEASE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_OPAQUE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.SET_OPAQUE)); + } - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_SET)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_ACQUIRE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_RELEASE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_PLAIN)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_ACQUIRE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_RELEASE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET_ACQUIRE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET_RELEASE)); + if (vhs.supportsAtomicAccess) { + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_SET)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_ACQUIRE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_RELEASE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_PLAIN)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_ACQUIRE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_RELEASE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET_ACQUIRE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET_RELEASE)); + } else { + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_SET)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_RELEASE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_PLAIN)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_RELEASE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET_RELEASE)); + } - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD_ACQUIRE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD_RELEASE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD_RELEASE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR_ACQUIRE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR_RELEASE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND_ACQUIRE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND_RELEASE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR_ACQUIRE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR_RELEASE)); + + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR_RELEASE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND_RELEASE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR_RELEASE)); } @Test(dataProvider = "typesProvider") @@ -180,9 +204,6 @@ public class VarHandleTestByteArrayAsDouble extends VarHandleBaseByteArrayTest { cases.add(new VarHandleSourceAccessTestCase( "index out of bounds", bav, vh, h -> testArrayIndexOutOfBounds(bas, h), false)); - cases.add(new VarHandleSourceAccessTestCase( - "misaligned access", bav, vh, h -> testArrayMisalignedAccess(bas, h), - false)); } else { ByteBufferSource bbs = (ByteBufferSource) bav; @@ -207,9 +228,11 @@ public class VarHandleTestByteArrayAsDouble extends VarHandleBaseByteArrayTest { cases.add(new VarHandleSourceAccessTestCase( "index out of bounds", bav, vh, h -> testArrayIndexOutOfBounds(bbs, h), false)); - cases.add(new VarHandleSourceAccessTestCase( - "misaligned access", bav, vh, h -> testArrayMisalignedAccess(bbs, h), - false)); + if (bbs.s.isDirect()) { + cases.add(new VarHandleSourceAccessTestCase( + "misaligned access", bav, vh, h -> testArrayMisalignedAccess(bbs, h), + false)); + } } } } @@ -243,76 +266,6 @@ public class VarHandleTestByteArrayAsDouble extends VarHandleBaseByteArrayTest { checkNPE(() -> { vh.set(array, ci, VALUE_1); }); - - checkNPE(() -> { - double x = (double) vh.getVolatile(array, ci); - }); - - checkNPE(() -> { - double x = (double) vh.getAcquire(array, ci); - }); - - checkNPE(() -> { - double x = (double) vh.getOpaque(array, ci); - }); - - checkNPE(() -> { - vh.setVolatile(array, ci, VALUE_1); - }); - - checkNPE(() -> { - vh.setRelease(array, ci, VALUE_1); - }); - - checkNPE(() -> { - vh.setOpaque(array, ci, VALUE_1); - }); - - checkNPE(() -> { - boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); - }); - - checkNPE(() -> { - double r = (double) vh.compareAndExchange(array, ci, VALUE_2, VALUE_1); - }); - - checkNPE(() -> { - double r = (double) vh.compareAndExchangeAcquire(array, ci, VALUE_2, VALUE_1); - }); - - checkNPE(() -> { - double r = (double) vh.compareAndExchangeRelease(array, ci, VALUE_2, VALUE_1); - }); - - checkNPE(() -> { - boolean r = vh.weakCompareAndSetPlain(array, ci, VALUE_1, VALUE_2); - }); - - checkNPE(() -> { - boolean r = vh.weakCompareAndSet(array, ci, VALUE_1, VALUE_2); - }); - - checkNPE(() -> { - boolean r = vh.weakCompareAndSetAcquire(array, ci, VALUE_1, VALUE_2); - }); - - checkNPE(() -> { - boolean r = vh.weakCompareAndSetRelease(array, ci, VALUE_1, VALUE_2); - }); - - checkNPE(() -> { - double o = (double) vh.getAndSet(array, ci, VALUE_1); - }); - - checkNPE(() -> { - double o = (double) vh.getAndSetAcquire(array, ci, VALUE_1); - }); - - checkNPE(() -> { - double o = (double) vh.getAndSetRelease(array, ci, VALUE_1); - }); - - } static void testArrayNPE(ByteBufferSource bs, VarHandleSource vhs) { @@ -404,6 +357,49 @@ public class VarHandleTestByteArrayAsDouble extends VarHandleBaseByteArrayTest { byte[] array = bs.s; int ci = 1; + checkUOE(() -> { + boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); + }); + + checkUOE(() -> { + double r = (double) vh.compareAndExchange(array, ci, VALUE_2, VALUE_1); + }); + + checkUOE(() -> { + double r = (double) vh.compareAndExchangeAcquire(array, ci, VALUE_2, VALUE_1); + }); + + checkUOE(() -> { + double r = (double) vh.compareAndExchangeRelease(array, ci, VALUE_2, VALUE_1); + }); + + checkUOE(() -> { + boolean r = vh.weakCompareAndSetPlain(array, ci, VALUE_1, VALUE_2); + }); + + checkUOE(() -> { + boolean r = vh.weakCompareAndSet(array, ci, VALUE_1, VALUE_2); + }); + + checkUOE(() -> { + boolean r = vh.weakCompareAndSetAcquire(array, ci, VALUE_1, VALUE_2); + }); + + checkUOE(() -> { + boolean r = vh.weakCompareAndSetRelease(array, ci, VALUE_1, VALUE_2); + }); + + checkUOE(() -> { + double o = (double) vh.getAndSet(array, ci, VALUE_1); + }); + + checkUOE(() -> { + double o = (double) vh.getAndSetAcquire(array, ci, VALUE_1); + }); + + checkUOE(() -> { + double o = (double) vh.getAndSetRelease(array, ci, VALUE_1); + }); checkUOE(() -> { double o = (double) vh.getAndAdd(array, ci, VALUE_1); @@ -466,7 +462,7 @@ public class VarHandleTestByteArrayAsDouble extends VarHandleBaseByteArrayTest { }); } - if (readOnly) { + if (readOnly && array.isDirect()) { checkROBE(() -> { vh.setVolatile(array, ci, VALUE_1); }); @@ -478,7 +474,6 @@ public class VarHandleTestByteArrayAsDouble extends VarHandleBaseByteArrayTest { checkROBE(() -> { vh.setOpaque(array, ci, VALUE_1); }); - checkROBE(() -> { boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); }); @@ -524,6 +519,9 @@ public class VarHandleTestByteArrayAsDouble extends VarHandleBaseByteArrayTest { }); + } + + if (array.isDirect()) { checkUOE(() -> { double o = (double) vh.getAndAdd(array, ci, VALUE_1); }); @@ -535,7 +533,6 @@ public class VarHandleTestByteArrayAsDouble extends VarHandleBaseByteArrayTest { checkUOE(() -> { double o = (double) vh.getAndAddRelease(array, ci, VALUE_1); }); - checkUOE(() -> { double o = (double) vh.getAndBitwiseOr(array, ci, VALUE_1); }); @@ -571,8 +568,61 @@ public class VarHandleTestByteArrayAsDouble extends VarHandleBaseByteArrayTest { checkUOE(() -> { double o = (double) vh.getAndBitwiseXorRelease(array, ci, VALUE_1); }); - } - else { + } else { + checkISE(() -> { + vh.setVolatile(array, ci, VALUE_1); + }); + + checkISE(() -> { + vh.setRelease(array, ci, VALUE_1); + }); + + checkISE(() -> { + vh.setOpaque(array, ci, VALUE_1); + }); + checkISE(() -> { + boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); + }); + + checkISE(() -> { + double r = (double) vh.compareAndExchange(array, ci, VALUE_2, VALUE_1); + }); + + checkISE(() -> { + double r = (double) vh.compareAndExchangeAcquire(array, ci, VALUE_2, VALUE_1); + }); + + checkISE(() -> { + double r = (double) vh.compareAndExchangeRelease(array, ci, VALUE_2, VALUE_1); + }); + + checkISE(() -> { + boolean r = vh.weakCompareAndSetPlain(array, ci, VALUE_1, VALUE_2); + }); + + checkISE(() -> { + boolean r = vh.weakCompareAndSet(array, ci, VALUE_1, VALUE_2); + }); + + checkISE(() -> { + boolean r = vh.weakCompareAndSetAcquire(array, ci, VALUE_1, VALUE_2); + }); + + checkISE(() -> { + boolean r = vh.weakCompareAndSetRelease(array, ci, VALUE_1, VALUE_2); + }); + + checkISE(() -> { + double o = (double) vh.getAndSet(array, ci, VALUE_1); + }); + + checkISE(() -> { + double o = (double) vh.getAndSetAcquire(array, ci, VALUE_1); + }); + + checkISE(() -> { + double o = (double) vh.getAndSetRelease(array, ci, VALUE_1); + }); checkUOE(() -> { double o = (double) vh.getAndAdd(array, ci, VALUE_1); }); @@ -638,77 +688,6 @@ public class VarHandleTestByteArrayAsDouble extends VarHandleBaseByteArrayTest { checkAIOOBE(() -> { vh.set(array, ci, VALUE_1); }); - - checkAIOOBE(() -> { - double x = (double) vh.getVolatile(array, ci); - }); - - checkAIOOBE(() -> { - double x = (double) vh.getAcquire(array, ci); - }); - - checkAIOOBE(() -> { - double x = (double) vh.getOpaque(array, ci); - }); - - checkAIOOBE(() -> { - vh.setVolatile(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - vh.setRelease(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - vh.setOpaque(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); - }); - - checkAIOOBE(() -> { - double r = (double) vh.compareAndExchange(array, ci, VALUE_2, VALUE_1); - }); - - checkAIOOBE(() -> { - double r = (double) vh.compareAndExchangeAcquire(array, ci, VALUE_2, VALUE_1); - }); - - checkAIOOBE(() -> { - double r = (double) vh.compareAndExchangeRelease(array, ci, VALUE_2, VALUE_1); - }); - - checkAIOOBE(() -> { - boolean r = vh.weakCompareAndSetPlain(array, ci, VALUE_1, VALUE_2); - }); - - checkAIOOBE(() -> { - boolean r = vh.weakCompareAndSet(array, ci, VALUE_1, VALUE_2); - }); - - checkAIOOBE(() -> { - boolean r = vh.weakCompareAndSetAcquire(array, ci, VALUE_1, VALUE_2); - }); - - checkAIOOBE(() -> { - boolean r = vh.weakCompareAndSetRelease(array, ci, VALUE_1, VALUE_2); - }); - - checkAIOOBE(() -> { - double o = (double) vh.getAndSet(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - double o = (double) vh.getAndSetAcquire(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - double o = (double) vh.getAndSetRelease(array, ci, VALUE_1); - }); - - - } } @@ -732,161 +711,78 @@ public class VarHandleTestByteArrayAsDouble extends VarHandleBaseByteArrayTest { }); } - checkIOOBE(() -> { - double x = (double) vh.getVolatile(array, ci); - }); - - checkIOOBE(() -> { - double x = (double) vh.getAcquire(array, ci); - }); - - checkIOOBE(() -> { - double x = (double) vh.getOpaque(array, ci); - }); - - if (!readOnly) { + if (array.isDirect()) { checkIOOBE(() -> { - vh.setVolatile(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - vh.setRelease(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - vh.setOpaque(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); - }); - - checkIOOBE(() -> { - double r = (double) vh.compareAndExchange(array, ci, VALUE_2, VALUE_1); - }); - - checkIOOBE(() -> { - double r = (double) vh.compareAndExchangeAcquire(array, ci, VALUE_2, VALUE_1); - }); - - checkIOOBE(() -> { - double r = (double) vh.compareAndExchangeRelease(array, ci, VALUE_2, VALUE_1); - }); - - checkIOOBE(() -> { - boolean r = vh.weakCompareAndSetPlain(array, ci, VALUE_1, VALUE_2); - }); - - checkIOOBE(() -> { - boolean r = vh.weakCompareAndSet(array, ci, VALUE_1, VALUE_2); - }); - - checkIOOBE(() -> { - boolean r = vh.weakCompareAndSetAcquire(array, ci, VALUE_1, VALUE_2); - }); - - checkIOOBE(() -> { - boolean r = vh.weakCompareAndSetRelease(array, ci, VALUE_1, VALUE_2); - }); - - checkIOOBE(() -> { - double o = (double) vh.getAndSet(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - double o = (double) vh.getAndSetAcquire(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - double o = (double) vh.getAndSetRelease(array, ci, VALUE_1); - }); - - - } - } - } - - static void testArrayMisalignedAccess(ByteArraySource bs, VarHandleSource vhs) throws Throwable { - VarHandle vh = vhs.s; - byte[] array = bs.s; - - int misalignmentAtZero = ByteBuffer.wrap(array).alignmentOffset(0, SIZE); - - int length = array.length - SIZE + 1; - for (int i = 0; i < length; i++) { - boolean iAligned = ((i + misalignmentAtZero) & (SIZE - 1)) == 0; - final int ci = i; - - if (!iAligned) { - checkISE(() -> { double x = (double) vh.getVolatile(array, ci); }); - checkISE(() -> { + checkIOOBE(() -> { double x = (double) vh.getAcquire(array, ci); }); - checkISE(() -> { + checkIOOBE(() -> { double x = (double) vh.getOpaque(array, ci); }); - checkISE(() -> { - vh.setVolatile(array, ci, VALUE_1); - }); + if (!readOnly) { + checkIOOBE(() -> { + vh.setVolatile(array, ci, VALUE_1); + }); - checkISE(() -> { - vh.setRelease(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + vh.setRelease(array, ci, VALUE_1); + }); - checkISE(() -> { - vh.setOpaque(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + vh.setOpaque(array, ci, VALUE_1); + }); - checkISE(() -> { - boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); - }); + checkIOOBE(() -> { + boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); + }); - checkISE(() -> { - double r = (double) vh.compareAndExchange(array, ci, VALUE_2, VALUE_1); - }); + checkIOOBE(() -> { + double r = (double) vh.compareAndExchange(array, ci, VALUE_2, VALUE_1); + }); - checkISE(() -> { - double r = (double) vh.compareAndExchangeAcquire(array, ci, VALUE_2, VALUE_1); - }); + checkIOOBE(() -> { + double r = (double) vh.compareAndExchangeAcquire(array, ci, VALUE_2, VALUE_1); + }); - checkISE(() -> { - double r = (double) vh.compareAndExchangeRelease(array, ci, VALUE_2, VALUE_1); - }); + checkIOOBE(() -> { + double r = (double) vh.compareAndExchangeRelease(array, ci, VALUE_2, VALUE_1); + }); - checkISE(() -> { - boolean r = vh.weakCompareAndSetPlain(array, ci, VALUE_1, VALUE_2); - }); + checkIOOBE(() -> { + boolean r = vh.weakCompareAndSetPlain(array, ci, VALUE_1, VALUE_2); + }); - checkISE(() -> { - boolean r = vh.weakCompareAndSet(array, ci, VALUE_1, VALUE_2); - }); + checkIOOBE(() -> { + boolean r = vh.weakCompareAndSet(array, ci, VALUE_1, VALUE_2); + }); - checkISE(() -> { - boolean r = vh.weakCompareAndSetAcquire(array, ci, VALUE_1, VALUE_2); - }); + checkIOOBE(() -> { + boolean r = vh.weakCompareAndSetAcquire(array, ci, VALUE_1, VALUE_2); + }); - checkISE(() -> { - boolean r = vh.weakCompareAndSetRelease(array, ci, VALUE_1, VALUE_2); - }); + checkIOOBE(() -> { + boolean r = vh.weakCompareAndSetRelease(array, ci, VALUE_1, VALUE_2); + }); - checkISE(() -> { - double o = (double) vh.getAndSet(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + double o = (double) vh.getAndSet(array, ci, VALUE_1); + }); - checkISE(() -> { - double o = (double) vh.getAndSetAcquire(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + double o = (double) vh.getAndSetAcquire(array, ci, VALUE_1); + }); - checkISE(() -> { - double o = (double) vh.getAndSetRelease(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + double o = (double) vh.getAndSetRelease(array, ci, VALUE_1); + }); + } } } } @@ -928,7 +824,6 @@ public class VarHandleTestByteArrayAsDouble extends VarHandleBaseByteArrayTest { checkISE(() -> { vh.setOpaque(array, ci, VALUE_1); }); - checkISE(() -> { boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); }); @@ -972,8 +867,6 @@ public class VarHandleTestByteArrayAsDouble extends VarHandleBaseByteArrayTest { checkISE(() -> { double o = (double) vh.getAndSetRelease(array, ci, VALUE_1); }); - - } } } @@ -983,204 +876,15 @@ public class VarHandleTestByteArrayAsDouble extends VarHandleBaseByteArrayTest { VarHandle vh = vhs.s; byte[] array = bs.s; - int misalignmentAtZero = ByteBuffer.wrap(array).alignmentOffset(0, SIZE); - bs.fill((byte) 0xff); int length = array.length - SIZE + 1; for (int i = 0; i < length; i++) { - boolean iAligned = ((i + misalignmentAtZero) & (SIZE - 1)) == 0; - // Plain { vh.set(array, i, VALUE_1); double x = (double) vh.get(array, i); assertEquals(x, VALUE_1, "get double value"); } - - - if (iAligned) { - // Volatile - { - vh.setVolatile(array, i, VALUE_2); - double x = (double) vh.getVolatile(array, i); - assertEquals(x, VALUE_2, "setVolatile double value"); - } - - // Lazy - { - vh.setRelease(array, i, VALUE_1); - double x = (double) vh.getAcquire(array, i); - assertEquals(x, VALUE_1, "setRelease double value"); - } - - // Opaque - { - vh.setOpaque(array, i, VALUE_2); - double x = (double) vh.getOpaque(array, i); - assertEquals(x, VALUE_2, "setOpaque double value"); - } - - vh.set(array, i, VALUE_1); - - // Compare - { - boolean r = vh.compareAndSet(array, i, VALUE_1, VALUE_2); - assertEquals(r, true, "success compareAndSet double"); - double x = (double) vh.get(array, i); - assertEquals(x, VALUE_2, "success compareAndSet double value"); - } - - { - boolean r = vh.compareAndSet(array, i, VALUE_1, VALUE_3); - assertEquals(r, false, "failing compareAndSet double"); - double x = (double) vh.get(array, i); - assertEquals(x, VALUE_2, "failing compareAndSet double value"); - } - - { - double r = (double) vh.compareAndExchange(array, i, VALUE_2, VALUE_1); - assertEquals(r, VALUE_2, "success compareAndExchange double"); - double x = (double) vh.get(array, i); - assertEquals(x, VALUE_1, "success compareAndExchange double value"); - } - - { - double r = (double) vh.compareAndExchange(array, i, VALUE_2, VALUE_3); - assertEquals(r, VALUE_1, "failing compareAndExchange double"); - double x = (double) vh.get(array, i); - assertEquals(x, VALUE_1, "failing compareAndExchange double value"); - } - - { - double r = (double) vh.compareAndExchangeAcquire(array, i, VALUE_1, VALUE_2); - assertEquals(r, VALUE_1, "success compareAndExchangeAcquire double"); - double x = (double) vh.get(array, i); - assertEquals(x, VALUE_2, "success compareAndExchangeAcquire double value"); - } - - { - double r = (double) vh.compareAndExchangeAcquire(array, i, VALUE_1, VALUE_3); - assertEquals(r, VALUE_2, "failing compareAndExchangeAcquire double"); - double x = (double) vh.get(array, i); - assertEquals(x, VALUE_2, "failing compareAndExchangeAcquire double value"); - } - - { - double r = (double) vh.compareAndExchangeRelease(array, i, VALUE_2, VALUE_1); - assertEquals(r, VALUE_2, "success compareAndExchangeRelease double"); - double x = (double) vh.get(array, i); - assertEquals(x, VALUE_1, "success compareAndExchangeRelease double value"); - } - - { - double r = (double) vh.compareAndExchangeRelease(array, i, VALUE_2, VALUE_3); - assertEquals(r, VALUE_1, "failing compareAndExchangeRelease double"); - double x = (double) vh.get(array, i); - assertEquals(x, VALUE_1, "failing compareAndExchangeRelease double value"); - } - - { - boolean success = false; - for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) { - success = vh.weakCompareAndSetPlain(array, i, VALUE_1, VALUE_2); - if (!success) weakDelay(); - } - assertEquals(success, true, "success weakCompareAndSetPlain double"); - double x = (double) vh.get(array, i); - assertEquals(x, VALUE_2, "success weakCompareAndSetPlain double value"); - } - - { - boolean success = vh.weakCompareAndSetPlain(array, i, VALUE_1, VALUE_3); - assertEquals(success, false, "failing weakCompareAndSetPlain double"); - double x = (double) vh.get(array, i); - assertEquals(x, VALUE_2, "failing weakCompareAndSetPlain double value"); - } - - { - boolean success = false; - for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) { - success = vh.weakCompareAndSetAcquire(array, i, VALUE_2, VALUE_1); - if (!success) weakDelay(); - } - assertEquals(success, true, "success weakCompareAndSetAcquire double"); - double x = (double) vh.get(array, i); - assertEquals(x, VALUE_1, "success weakCompareAndSetAcquire double"); - } - - { - boolean success = vh.weakCompareAndSetAcquire(array, i, VALUE_2, VALUE_3); - assertEquals(success, false, "failing weakCompareAndSetAcquire double"); - double x = (double) vh.get(array, i); - assertEquals(x, VALUE_1, "failing weakCompareAndSetAcquire double value"); - } - - { - boolean success = false; - for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) { - success = vh.weakCompareAndSetRelease(array, i, VALUE_1, VALUE_2); - if (!success) weakDelay(); - } - assertEquals(success, true, "success weakCompareAndSetRelease double"); - double x = (double) vh.get(array, i); - assertEquals(x, VALUE_2, "success weakCompareAndSetRelease double"); - } - - { - boolean success = vh.weakCompareAndSetRelease(array, i, VALUE_1, VALUE_3); - assertEquals(success, false, "failing weakCompareAndSetRelease double"); - double x = (double) vh.get(array, i); - assertEquals(x, VALUE_2, "failing weakCompareAndSetRelease double value"); - } - - { - boolean success = false; - for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) { - success = vh.weakCompareAndSet(array, i, VALUE_2, VALUE_1); - if (!success) weakDelay(); - } - assertEquals(success, true, "success weakCompareAndSet double"); - double x = (double) vh.get(array, i); - assertEquals(x, VALUE_1, "success weakCompareAndSet double"); - } - - { - boolean success = vh.weakCompareAndSet(array, i, VALUE_2, VALUE_3); - assertEquals(success, false, "failing weakCompareAndSet double"); - double x = (double) vh.get(array, i); - assertEquals(x, VALUE_1, "failing weakCompareAndSet double value"); - } - - // Compare set and get - { - vh.set(array, i, VALUE_1); - - double o = (double) vh.getAndSet(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndSet double"); - double x = (double) vh.get(array, i); - assertEquals(x, VALUE_2, "getAndSet double value"); - } - - { - vh.set(array, i, VALUE_1); - - double o = (double) vh.getAndSetAcquire(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndSetAcquire double"); - double x = (double) vh.get(array, i); - assertEquals(x, VALUE_2, "getAndSetAcquire double value"); - } - - { - vh.set(array, i, VALUE_1); - - double o = (double) vh.getAndSetRelease(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndSetRelease double"); - double x = (double) vh.get(array, i); - assertEquals(x, VALUE_2, "getAndSetRelease double value"); - } - - - } } } @@ -1189,12 +893,10 @@ public class VarHandleTestByteArrayAsDouble extends VarHandleBaseByteArrayTest { VarHandle vh = vhs.s; ByteBuffer array = bs.s; - int misalignmentAtZero = array.alignmentOffset(0, SIZE); - bs.fill((byte) 0xff); int length = array.limit() - SIZE + 1; for (int i = 0; i < length; i++) { - boolean iAligned = ((i + misalignmentAtZero) & (SIZE - 1)) == 0; + boolean iAligned = array.isDirect() ? ((i + array.alignmentOffset(0, SIZE)) & (SIZE - 1)) == 0 : false; // Plain { @@ -1393,15 +1095,13 @@ public class VarHandleTestByteArrayAsDouble extends VarHandleBaseByteArrayTest { VarHandle vh = vhs.s; ByteBuffer array = bs.s; - int misalignmentAtZero = array.alignmentOffset(0, SIZE); - ByteBuffer bb = ByteBuffer.allocate(SIZE); bb.order(MemoryMode.BIG_ENDIAN.isSet(vhs.memoryModes) ? ByteOrder.BIG_ENDIAN : ByteOrder.LITTLE_ENDIAN); bs.fill(bb.putDouble(0, VALUE_2).array()); int length = array.limit() - SIZE + 1; for (int i = 0; i < length; i++) { - boolean iAligned = ((i + misalignmentAtZero) & (SIZE - 1)) == 0; + boolean iAligned = array.isDirect() ? ((i + array.alignmentOffset(0, SIZE)) & (SIZE - 1)) == 0 : false; double v = MemoryMode.BIG_ENDIAN.isSet(vhs.memoryModes) ? rotateLeft(VALUE_2, (i % SIZE) << 3) diff --git a/test/jdk/java/lang/invoke/VarHandles/VarHandleTestByteArrayAsFloat.java b/test/jdk/java/lang/invoke/VarHandles/VarHandleTestByteArrayAsFloat.java index e1c8413142c..5c3854b6068 100644 --- a/test/jdk/java/lang/invoke/VarHandles/VarHandleTestByteArrayAsFloat.java +++ b/test/jdk/java/lang/invoke/VarHandles/VarHandleTestByteArrayAsFloat.java @@ -72,12 +72,12 @@ public class VarHandleTestByteArrayAsFloat extends VarHandleBaseByteArrayTest { arrayType = int[].class; } VarHandleSource aeh = new VarHandleSource( - MethodHandles.byteArrayViewVarHandle(arrayType, bo), + MethodHandles.byteArrayViewVarHandle(arrayType, bo), false, endianess, MemoryMode.READ_WRITE); vhss.add(aeh); VarHandleSource bbh = new VarHandleSource( - MethodHandles.byteBufferViewVarHandle(arrayType, bo), + MethodHandles.byteBufferViewVarHandle(arrayType, bo), true, endianess, MemoryMode.READ_WRITE); vhss.add(bbh); } @@ -114,38 +114,62 @@ public class VarHandleTestByteArrayAsFloat extends VarHandleBaseByteArrayTest { assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET)); assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_VOLATILE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_VOLATILE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_ACQUIRE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_RELEASE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_OPAQUE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_OPAQUE)); + if (vhs.supportsAtomicAccess) { + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_VOLATILE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_VOLATILE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_ACQUIRE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_RELEASE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_OPAQUE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_OPAQUE)); + } else { + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_VOLATILE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.SET_VOLATILE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.SET_RELEASE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_OPAQUE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.SET_OPAQUE)); + } - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_SET)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_ACQUIRE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_RELEASE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_PLAIN)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_ACQUIRE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_RELEASE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET_ACQUIRE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET_RELEASE)); + if (vhs.supportsAtomicAccess) { + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_SET)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_ACQUIRE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_RELEASE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_PLAIN)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_ACQUIRE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_RELEASE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET_ACQUIRE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET_RELEASE)); + } else { + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_SET)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_RELEASE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_PLAIN)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_RELEASE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET_RELEASE)); + } - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD_ACQUIRE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD_RELEASE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD_RELEASE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR_ACQUIRE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR_RELEASE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND_ACQUIRE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND_RELEASE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR_ACQUIRE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR_RELEASE)); + + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR_RELEASE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND_RELEASE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR_RELEASE)); } @Test(dataProvider = "typesProvider") @@ -180,9 +204,6 @@ public class VarHandleTestByteArrayAsFloat extends VarHandleBaseByteArrayTest { cases.add(new VarHandleSourceAccessTestCase( "index out of bounds", bav, vh, h -> testArrayIndexOutOfBounds(bas, h), false)); - cases.add(new VarHandleSourceAccessTestCase( - "misaligned access", bav, vh, h -> testArrayMisalignedAccess(bas, h), - false)); } else { ByteBufferSource bbs = (ByteBufferSource) bav; @@ -207,9 +228,11 @@ public class VarHandleTestByteArrayAsFloat extends VarHandleBaseByteArrayTest { cases.add(new VarHandleSourceAccessTestCase( "index out of bounds", bav, vh, h -> testArrayIndexOutOfBounds(bbs, h), false)); - cases.add(new VarHandleSourceAccessTestCase( - "misaligned access", bav, vh, h -> testArrayMisalignedAccess(bbs, h), - false)); + if (bbs.s.isDirect()) { + cases.add(new VarHandleSourceAccessTestCase( + "misaligned access", bav, vh, h -> testArrayMisalignedAccess(bbs, h), + false)); + } } } } @@ -243,76 +266,6 @@ public class VarHandleTestByteArrayAsFloat extends VarHandleBaseByteArrayTest { checkNPE(() -> { vh.set(array, ci, VALUE_1); }); - - checkNPE(() -> { - float x = (float) vh.getVolatile(array, ci); - }); - - checkNPE(() -> { - float x = (float) vh.getAcquire(array, ci); - }); - - checkNPE(() -> { - float x = (float) vh.getOpaque(array, ci); - }); - - checkNPE(() -> { - vh.setVolatile(array, ci, VALUE_1); - }); - - checkNPE(() -> { - vh.setRelease(array, ci, VALUE_1); - }); - - checkNPE(() -> { - vh.setOpaque(array, ci, VALUE_1); - }); - - checkNPE(() -> { - boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); - }); - - checkNPE(() -> { - float r = (float) vh.compareAndExchange(array, ci, VALUE_2, VALUE_1); - }); - - checkNPE(() -> { - float r = (float) vh.compareAndExchangeAcquire(array, ci, VALUE_2, VALUE_1); - }); - - checkNPE(() -> { - float r = (float) vh.compareAndExchangeRelease(array, ci, VALUE_2, VALUE_1); - }); - - checkNPE(() -> { - boolean r = vh.weakCompareAndSetPlain(array, ci, VALUE_1, VALUE_2); - }); - - checkNPE(() -> { - boolean r = vh.weakCompareAndSet(array, ci, VALUE_1, VALUE_2); - }); - - checkNPE(() -> { - boolean r = vh.weakCompareAndSetAcquire(array, ci, VALUE_1, VALUE_2); - }); - - checkNPE(() -> { - boolean r = vh.weakCompareAndSetRelease(array, ci, VALUE_1, VALUE_2); - }); - - checkNPE(() -> { - float o = (float) vh.getAndSet(array, ci, VALUE_1); - }); - - checkNPE(() -> { - float o = (float) vh.getAndSetAcquire(array, ci, VALUE_1); - }); - - checkNPE(() -> { - float o = (float) vh.getAndSetRelease(array, ci, VALUE_1); - }); - - } static void testArrayNPE(ByteBufferSource bs, VarHandleSource vhs) { @@ -404,6 +357,49 @@ public class VarHandleTestByteArrayAsFloat extends VarHandleBaseByteArrayTest { byte[] array = bs.s; int ci = 1; + checkUOE(() -> { + boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); + }); + + checkUOE(() -> { + float r = (float) vh.compareAndExchange(array, ci, VALUE_2, VALUE_1); + }); + + checkUOE(() -> { + float r = (float) vh.compareAndExchangeAcquire(array, ci, VALUE_2, VALUE_1); + }); + + checkUOE(() -> { + float r = (float) vh.compareAndExchangeRelease(array, ci, VALUE_2, VALUE_1); + }); + + checkUOE(() -> { + boolean r = vh.weakCompareAndSetPlain(array, ci, VALUE_1, VALUE_2); + }); + + checkUOE(() -> { + boolean r = vh.weakCompareAndSet(array, ci, VALUE_1, VALUE_2); + }); + + checkUOE(() -> { + boolean r = vh.weakCompareAndSetAcquire(array, ci, VALUE_1, VALUE_2); + }); + + checkUOE(() -> { + boolean r = vh.weakCompareAndSetRelease(array, ci, VALUE_1, VALUE_2); + }); + + checkUOE(() -> { + float o = (float) vh.getAndSet(array, ci, VALUE_1); + }); + + checkUOE(() -> { + float o = (float) vh.getAndSetAcquire(array, ci, VALUE_1); + }); + + checkUOE(() -> { + float o = (float) vh.getAndSetRelease(array, ci, VALUE_1); + }); checkUOE(() -> { float o = (float) vh.getAndAdd(array, ci, VALUE_1); @@ -466,7 +462,7 @@ public class VarHandleTestByteArrayAsFloat extends VarHandleBaseByteArrayTest { }); } - if (readOnly) { + if (readOnly && array.isDirect()) { checkROBE(() -> { vh.setVolatile(array, ci, VALUE_1); }); @@ -478,7 +474,6 @@ public class VarHandleTestByteArrayAsFloat extends VarHandleBaseByteArrayTest { checkROBE(() -> { vh.setOpaque(array, ci, VALUE_1); }); - checkROBE(() -> { boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); }); @@ -524,6 +519,9 @@ public class VarHandleTestByteArrayAsFloat extends VarHandleBaseByteArrayTest { }); + } + + if (array.isDirect()) { checkUOE(() -> { float o = (float) vh.getAndAdd(array, ci, VALUE_1); }); @@ -535,7 +533,6 @@ public class VarHandleTestByteArrayAsFloat extends VarHandleBaseByteArrayTest { checkUOE(() -> { float o = (float) vh.getAndAddRelease(array, ci, VALUE_1); }); - checkUOE(() -> { float o = (float) vh.getAndBitwiseOr(array, ci, VALUE_1); }); @@ -571,8 +568,61 @@ public class VarHandleTestByteArrayAsFloat extends VarHandleBaseByteArrayTest { checkUOE(() -> { float o = (float) vh.getAndBitwiseXorRelease(array, ci, VALUE_1); }); - } - else { + } else { + checkISE(() -> { + vh.setVolatile(array, ci, VALUE_1); + }); + + checkISE(() -> { + vh.setRelease(array, ci, VALUE_1); + }); + + checkISE(() -> { + vh.setOpaque(array, ci, VALUE_1); + }); + checkISE(() -> { + boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); + }); + + checkISE(() -> { + float r = (float) vh.compareAndExchange(array, ci, VALUE_2, VALUE_1); + }); + + checkISE(() -> { + float r = (float) vh.compareAndExchangeAcquire(array, ci, VALUE_2, VALUE_1); + }); + + checkISE(() -> { + float r = (float) vh.compareAndExchangeRelease(array, ci, VALUE_2, VALUE_1); + }); + + checkISE(() -> { + boolean r = vh.weakCompareAndSetPlain(array, ci, VALUE_1, VALUE_2); + }); + + checkISE(() -> { + boolean r = vh.weakCompareAndSet(array, ci, VALUE_1, VALUE_2); + }); + + checkISE(() -> { + boolean r = vh.weakCompareAndSetAcquire(array, ci, VALUE_1, VALUE_2); + }); + + checkISE(() -> { + boolean r = vh.weakCompareAndSetRelease(array, ci, VALUE_1, VALUE_2); + }); + + checkISE(() -> { + float o = (float) vh.getAndSet(array, ci, VALUE_1); + }); + + checkISE(() -> { + float o = (float) vh.getAndSetAcquire(array, ci, VALUE_1); + }); + + checkISE(() -> { + float o = (float) vh.getAndSetRelease(array, ci, VALUE_1); + }); checkUOE(() -> { float o = (float) vh.getAndAdd(array, ci, VALUE_1); }); @@ -638,77 +688,6 @@ public class VarHandleTestByteArrayAsFloat extends VarHandleBaseByteArrayTest { checkAIOOBE(() -> { vh.set(array, ci, VALUE_1); }); - - checkAIOOBE(() -> { - float x = (float) vh.getVolatile(array, ci); - }); - - checkAIOOBE(() -> { - float x = (float) vh.getAcquire(array, ci); - }); - - checkAIOOBE(() -> { - float x = (float) vh.getOpaque(array, ci); - }); - - checkAIOOBE(() -> { - vh.setVolatile(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - vh.setRelease(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - vh.setOpaque(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); - }); - - checkAIOOBE(() -> { - float r = (float) vh.compareAndExchange(array, ci, VALUE_2, VALUE_1); - }); - - checkAIOOBE(() -> { - float r = (float) vh.compareAndExchangeAcquire(array, ci, VALUE_2, VALUE_1); - }); - - checkAIOOBE(() -> { - float r = (float) vh.compareAndExchangeRelease(array, ci, VALUE_2, VALUE_1); - }); - - checkAIOOBE(() -> { - boolean r = vh.weakCompareAndSetPlain(array, ci, VALUE_1, VALUE_2); - }); - - checkAIOOBE(() -> { - boolean r = vh.weakCompareAndSet(array, ci, VALUE_1, VALUE_2); - }); - - checkAIOOBE(() -> { - boolean r = vh.weakCompareAndSetAcquire(array, ci, VALUE_1, VALUE_2); - }); - - checkAIOOBE(() -> { - boolean r = vh.weakCompareAndSetRelease(array, ci, VALUE_1, VALUE_2); - }); - - checkAIOOBE(() -> { - float o = (float) vh.getAndSet(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - float o = (float) vh.getAndSetAcquire(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - float o = (float) vh.getAndSetRelease(array, ci, VALUE_1); - }); - - - } } @@ -732,161 +711,78 @@ public class VarHandleTestByteArrayAsFloat extends VarHandleBaseByteArrayTest { }); } - checkIOOBE(() -> { - float x = (float) vh.getVolatile(array, ci); - }); - - checkIOOBE(() -> { - float x = (float) vh.getAcquire(array, ci); - }); - - checkIOOBE(() -> { - float x = (float) vh.getOpaque(array, ci); - }); - - if (!readOnly) { + if (array.isDirect()) { checkIOOBE(() -> { - vh.setVolatile(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - vh.setRelease(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - vh.setOpaque(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); - }); - - checkIOOBE(() -> { - float r = (float) vh.compareAndExchange(array, ci, VALUE_2, VALUE_1); - }); - - checkIOOBE(() -> { - float r = (float) vh.compareAndExchangeAcquire(array, ci, VALUE_2, VALUE_1); - }); - - checkIOOBE(() -> { - float r = (float) vh.compareAndExchangeRelease(array, ci, VALUE_2, VALUE_1); - }); - - checkIOOBE(() -> { - boolean r = vh.weakCompareAndSetPlain(array, ci, VALUE_1, VALUE_2); - }); - - checkIOOBE(() -> { - boolean r = vh.weakCompareAndSet(array, ci, VALUE_1, VALUE_2); - }); - - checkIOOBE(() -> { - boolean r = vh.weakCompareAndSetAcquire(array, ci, VALUE_1, VALUE_2); - }); - - checkIOOBE(() -> { - boolean r = vh.weakCompareAndSetRelease(array, ci, VALUE_1, VALUE_2); - }); - - checkIOOBE(() -> { - float o = (float) vh.getAndSet(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - float o = (float) vh.getAndSetAcquire(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - float o = (float) vh.getAndSetRelease(array, ci, VALUE_1); - }); - - - } - } - } - - static void testArrayMisalignedAccess(ByteArraySource bs, VarHandleSource vhs) throws Throwable { - VarHandle vh = vhs.s; - byte[] array = bs.s; - - int misalignmentAtZero = ByteBuffer.wrap(array).alignmentOffset(0, SIZE); - - int length = array.length - SIZE + 1; - for (int i = 0; i < length; i++) { - boolean iAligned = ((i + misalignmentAtZero) & (SIZE - 1)) == 0; - final int ci = i; - - if (!iAligned) { - checkISE(() -> { float x = (float) vh.getVolatile(array, ci); }); - checkISE(() -> { + checkIOOBE(() -> { float x = (float) vh.getAcquire(array, ci); }); - checkISE(() -> { + checkIOOBE(() -> { float x = (float) vh.getOpaque(array, ci); }); - checkISE(() -> { - vh.setVolatile(array, ci, VALUE_1); - }); + if (!readOnly) { + checkIOOBE(() -> { + vh.setVolatile(array, ci, VALUE_1); + }); - checkISE(() -> { - vh.setRelease(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + vh.setRelease(array, ci, VALUE_1); + }); - checkISE(() -> { - vh.setOpaque(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + vh.setOpaque(array, ci, VALUE_1); + }); - checkISE(() -> { - boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); - }); + checkIOOBE(() -> { + boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); + }); - checkISE(() -> { - float r = (float) vh.compareAndExchange(array, ci, VALUE_2, VALUE_1); - }); + checkIOOBE(() -> { + float r = (float) vh.compareAndExchange(array, ci, VALUE_2, VALUE_1); + }); - checkISE(() -> { - float r = (float) vh.compareAndExchangeAcquire(array, ci, VALUE_2, VALUE_1); - }); + checkIOOBE(() -> { + float r = (float) vh.compareAndExchangeAcquire(array, ci, VALUE_2, VALUE_1); + }); - checkISE(() -> { - float r = (float) vh.compareAndExchangeRelease(array, ci, VALUE_2, VALUE_1); - }); + checkIOOBE(() -> { + float r = (float) vh.compareAndExchangeRelease(array, ci, VALUE_2, VALUE_1); + }); - checkISE(() -> { - boolean r = vh.weakCompareAndSetPlain(array, ci, VALUE_1, VALUE_2); - }); + checkIOOBE(() -> { + boolean r = vh.weakCompareAndSetPlain(array, ci, VALUE_1, VALUE_2); + }); - checkISE(() -> { - boolean r = vh.weakCompareAndSet(array, ci, VALUE_1, VALUE_2); - }); + checkIOOBE(() -> { + boolean r = vh.weakCompareAndSet(array, ci, VALUE_1, VALUE_2); + }); - checkISE(() -> { - boolean r = vh.weakCompareAndSetAcquire(array, ci, VALUE_1, VALUE_2); - }); + checkIOOBE(() -> { + boolean r = vh.weakCompareAndSetAcquire(array, ci, VALUE_1, VALUE_2); + }); - checkISE(() -> { - boolean r = vh.weakCompareAndSetRelease(array, ci, VALUE_1, VALUE_2); - }); + checkIOOBE(() -> { + boolean r = vh.weakCompareAndSetRelease(array, ci, VALUE_1, VALUE_2); + }); - checkISE(() -> { - float o = (float) vh.getAndSet(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + float o = (float) vh.getAndSet(array, ci, VALUE_1); + }); - checkISE(() -> { - float o = (float) vh.getAndSetAcquire(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + float o = (float) vh.getAndSetAcquire(array, ci, VALUE_1); + }); - checkISE(() -> { - float o = (float) vh.getAndSetRelease(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + float o = (float) vh.getAndSetRelease(array, ci, VALUE_1); + }); + } } } } @@ -928,7 +824,6 @@ public class VarHandleTestByteArrayAsFloat extends VarHandleBaseByteArrayTest { checkISE(() -> { vh.setOpaque(array, ci, VALUE_1); }); - checkISE(() -> { boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); }); @@ -972,8 +867,6 @@ public class VarHandleTestByteArrayAsFloat extends VarHandleBaseByteArrayTest { checkISE(() -> { float o = (float) vh.getAndSetRelease(array, ci, VALUE_1); }); - - } } } @@ -983,204 +876,15 @@ public class VarHandleTestByteArrayAsFloat extends VarHandleBaseByteArrayTest { VarHandle vh = vhs.s; byte[] array = bs.s; - int misalignmentAtZero = ByteBuffer.wrap(array).alignmentOffset(0, SIZE); - bs.fill((byte) 0xff); int length = array.length - SIZE + 1; for (int i = 0; i < length; i++) { - boolean iAligned = ((i + misalignmentAtZero) & (SIZE - 1)) == 0; - // Plain { vh.set(array, i, VALUE_1); float x = (float) vh.get(array, i); assertEquals(x, VALUE_1, "get float value"); } - - - if (iAligned) { - // Volatile - { - vh.setVolatile(array, i, VALUE_2); - float x = (float) vh.getVolatile(array, i); - assertEquals(x, VALUE_2, "setVolatile float value"); - } - - // Lazy - { - vh.setRelease(array, i, VALUE_1); - float x = (float) vh.getAcquire(array, i); - assertEquals(x, VALUE_1, "setRelease float value"); - } - - // Opaque - { - vh.setOpaque(array, i, VALUE_2); - float x = (float) vh.getOpaque(array, i); - assertEquals(x, VALUE_2, "setOpaque float value"); - } - - vh.set(array, i, VALUE_1); - - // Compare - { - boolean r = vh.compareAndSet(array, i, VALUE_1, VALUE_2); - assertEquals(r, true, "success compareAndSet float"); - float x = (float) vh.get(array, i); - assertEquals(x, VALUE_2, "success compareAndSet float value"); - } - - { - boolean r = vh.compareAndSet(array, i, VALUE_1, VALUE_3); - assertEquals(r, false, "failing compareAndSet float"); - float x = (float) vh.get(array, i); - assertEquals(x, VALUE_2, "failing compareAndSet float value"); - } - - { - float r = (float) vh.compareAndExchange(array, i, VALUE_2, VALUE_1); - assertEquals(r, VALUE_2, "success compareAndExchange float"); - float x = (float) vh.get(array, i); - assertEquals(x, VALUE_1, "success compareAndExchange float value"); - } - - { - float r = (float) vh.compareAndExchange(array, i, VALUE_2, VALUE_3); - assertEquals(r, VALUE_1, "failing compareAndExchange float"); - float x = (float) vh.get(array, i); - assertEquals(x, VALUE_1, "failing compareAndExchange float value"); - } - - { - float r = (float) vh.compareAndExchangeAcquire(array, i, VALUE_1, VALUE_2); - assertEquals(r, VALUE_1, "success compareAndExchangeAcquire float"); - float x = (float) vh.get(array, i); - assertEquals(x, VALUE_2, "success compareAndExchangeAcquire float value"); - } - - { - float r = (float) vh.compareAndExchangeAcquire(array, i, VALUE_1, VALUE_3); - assertEquals(r, VALUE_2, "failing compareAndExchangeAcquire float"); - float x = (float) vh.get(array, i); - assertEquals(x, VALUE_2, "failing compareAndExchangeAcquire float value"); - } - - { - float r = (float) vh.compareAndExchangeRelease(array, i, VALUE_2, VALUE_1); - assertEquals(r, VALUE_2, "success compareAndExchangeRelease float"); - float x = (float) vh.get(array, i); - assertEquals(x, VALUE_1, "success compareAndExchangeRelease float value"); - } - - { - float r = (float) vh.compareAndExchangeRelease(array, i, VALUE_2, VALUE_3); - assertEquals(r, VALUE_1, "failing compareAndExchangeRelease float"); - float x = (float) vh.get(array, i); - assertEquals(x, VALUE_1, "failing compareAndExchangeRelease float value"); - } - - { - boolean success = false; - for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) { - success = vh.weakCompareAndSetPlain(array, i, VALUE_1, VALUE_2); - if (!success) weakDelay(); - } - assertEquals(success, true, "success weakCompareAndSetPlain float"); - float x = (float) vh.get(array, i); - assertEquals(x, VALUE_2, "success weakCompareAndSetPlain float value"); - } - - { - boolean success = vh.weakCompareAndSetPlain(array, i, VALUE_1, VALUE_3); - assertEquals(success, false, "failing weakCompareAndSetPlain float"); - float x = (float) vh.get(array, i); - assertEquals(x, VALUE_2, "failing weakCompareAndSetPlain float value"); - } - - { - boolean success = false; - for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) { - success = vh.weakCompareAndSetAcquire(array, i, VALUE_2, VALUE_1); - if (!success) weakDelay(); - } - assertEquals(success, true, "success weakCompareAndSetAcquire float"); - float x = (float) vh.get(array, i); - assertEquals(x, VALUE_1, "success weakCompareAndSetAcquire float"); - } - - { - boolean success = vh.weakCompareAndSetAcquire(array, i, VALUE_2, VALUE_3); - assertEquals(success, false, "failing weakCompareAndSetAcquire float"); - float x = (float) vh.get(array, i); - assertEquals(x, VALUE_1, "failing weakCompareAndSetAcquire float value"); - } - - { - boolean success = false; - for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) { - success = vh.weakCompareAndSetRelease(array, i, VALUE_1, VALUE_2); - if (!success) weakDelay(); - } - assertEquals(success, true, "success weakCompareAndSetRelease float"); - float x = (float) vh.get(array, i); - assertEquals(x, VALUE_2, "success weakCompareAndSetRelease float"); - } - - { - boolean success = vh.weakCompareAndSetRelease(array, i, VALUE_1, VALUE_3); - assertEquals(success, false, "failing weakCompareAndSetRelease float"); - float x = (float) vh.get(array, i); - assertEquals(x, VALUE_2, "failing weakCompareAndSetRelease float value"); - } - - { - boolean success = false; - for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) { - success = vh.weakCompareAndSet(array, i, VALUE_2, VALUE_1); - if (!success) weakDelay(); - } - assertEquals(success, true, "success weakCompareAndSet float"); - float x = (float) vh.get(array, i); - assertEquals(x, VALUE_1, "success weakCompareAndSet float"); - } - - { - boolean success = vh.weakCompareAndSet(array, i, VALUE_2, VALUE_3); - assertEquals(success, false, "failing weakCompareAndSet float"); - float x = (float) vh.get(array, i); - assertEquals(x, VALUE_1, "failing weakCompareAndSet float value"); - } - - // Compare set and get - { - vh.set(array, i, VALUE_1); - - float o = (float) vh.getAndSet(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndSet float"); - float x = (float) vh.get(array, i); - assertEquals(x, VALUE_2, "getAndSet float value"); - } - - { - vh.set(array, i, VALUE_1); - - float o = (float) vh.getAndSetAcquire(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndSetAcquire float"); - float x = (float) vh.get(array, i); - assertEquals(x, VALUE_2, "getAndSetAcquire float value"); - } - - { - vh.set(array, i, VALUE_1); - - float o = (float) vh.getAndSetRelease(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndSetRelease float"); - float x = (float) vh.get(array, i); - assertEquals(x, VALUE_2, "getAndSetRelease float value"); - } - - - } } } @@ -1189,12 +893,10 @@ public class VarHandleTestByteArrayAsFloat extends VarHandleBaseByteArrayTest { VarHandle vh = vhs.s; ByteBuffer array = bs.s; - int misalignmentAtZero = array.alignmentOffset(0, SIZE); - bs.fill((byte) 0xff); int length = array.limit() - SIZE + 1; for (int i = 0; i < length; i++) { - boolean iAligned = ((i + misalignmentAtZero) & (SIZE - 1)) == 0; + boolean iAligned = array.isDirect() ? ((i + array.alignmentOffset(0, SIZE)) & (SIZE - 1)) == 0 : false; // Plain { @@ -1393,15 +1095,13 @@ public class VarHandleTestByteArrayAsFloat extends VarHandleBaseByteArrayTest { VarHandle vh = vhs.s; ByteBuffer array = bs.s; - int misalignmentAtZero = array.alignmentOffset(0, SIZE); - ByteBuffer bb = ByteBuffer.allocate(SIZE); bb.order(MemoryMode.BIG_ENDIAN.isSet(vhs.memoryModes) ? ByteOrder.BIG_ENDIAN : ByteOrder.LITTLE_ENDIAN); bs.fill(bb.putFloat(0, VALUE_2).array()); int length = array.limit() - SIZE + 1; for (int i = 0; i < length; i++) { - boolean iAligned = ((i + misalignmentAtZero) & (SIZE - 1)) == 0; + boolean iAligned = array.isDirect() ? ((i + array.alignmentOffset(0, SIZE)) & (SIZE - 1)) == 0 : false; float v = MemoryMode.BIG_ENDIAN.isSet(vhs.memoryModes) ? rotateLeft(VALUE_2, (i % SIZE) << 3) diff --git a/test/jdk/java/lang/invoke/VarHandles/VarHandleTestByteArrayAsInt.java b/test/jdk/java/lang/invoke/VarHandles/VarHandleTestByteArrayAsInt.java index 3f6066c57bb..a03a6248a0f 100644 --- a/test/jdk/java/lang/invoke/VarHandles/VarHandleTestByteArrayAsInt.java +++ b/test/jdk/java/lang/invoke/VarHandles/VarHandleTestByteArrayAsInt.java @@ -72,12 +72,12 @@ public class VarHandleTestByteArrayAsInt extends VarHandleBaseByteArrayTest { arrayType = long[].class; } VarHandleSource aeh = new VarHandleSource( - MethodHandles.byteArrayViewVarHandle(arrayType, bo), + MethodHandles.byteArrayViewVarHandle(arrayType, bo), false, endianess, MemoryMode.READ_WRITE); vhss.add(aeh); VarHandleSource bbh = new VarHandleSource( - MethodHandles.byteBufferViewVarHandle(arrayType, bo), + MethodHandles.byteBufferViewVarHandle(arrayType, bo), true, endianess, MemoryMode.READ_WRITE); vhss.add(bbh); } @@ -114,38 +114,80 @@ public class VarHandleTestByteArrayAsInt extends VarHandleBaseByteArrayTest { assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET)); assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_VOLATILE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_VOLATILE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_ACQUIRE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_RELEASE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_OPAQUE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_OPAQUE)); + if (vhs.supportsAtomicAccess) { + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_VOLATILE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_VOLATILE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_ACQUIRE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_RELEASE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_OPAQUE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_OPAQUE)); + } else { + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_VOLATILE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.SET_VOLATILE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.SET_RELEASE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_OPAQUE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.SET_OPAQUE)); + } - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_SET)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_ACQUIRE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_RELEASE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_PLAIN)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_ACQUIRE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_RELEASE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET_ACQUIRE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET_RELEASE)); + if (vhs.supportsAtomicAccess) { + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_SET)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_ACQUIRE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_RELEASE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_PLAIN)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_ACQUIRE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_RELEASE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET_ACQUIRE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET_RELEASE)); + } else { + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_SET)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_RELEASE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_PLAIN)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_RELEASE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET_RELEASE)); + } - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD_ACQUIRE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD_RELEASE)); + if (vhs.supportsAtomicAccess) { + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD_ACQUIRE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD_RELEASE)); + } else { + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD_RELEASE)); + } - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR_ACQUIRE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR_RELEASE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND_ACQUIRE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND_RELEASE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR_ACQUIRE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR_RELEASE)); + + if (vhs.supportsAtomicAccess) { + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR_ACQUIRE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR_RELEASE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND_ACQUIRE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND_RELEASE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR_ACQUIRE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR_RELEASE)); + } else { + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR_RELEASE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND_RELEASE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR_RELEASE)); + } } @Test(dataProvider = "typesProvider") @@ -180,9 +222,6 @@ public class VarHandleTestByteArrayAsInt extends VarHandleBaseByteArrayTest { cases.add(new VarHandleSourceAccessTestCase( "index out of bounds", bav, vh, h -> testArrayIndexOutOfBounds(bas, h), false)); - cases.add(new VarHandleSourceAccessTestCase( - "misaligned access", bav, vh, h -> testArrayMisalignedAccess(bas, h), - false)); } else { ByteBufferSource bbs = (ByteBufferSource) bav; @@ -207,9 +246,11 @@ public class VarHandleTestByteArrayAsInt extends VarHandleBaseByteArrayTest { cases.add(new VarHandleSourceAccessTestCase( "index out of bounds", bav, vh, h -> testArrayIndexOutOfBounds(bbs, h), false)); - cases.add(new VarHandleSourceAccessTestCase( - "misaligned access", bav, vh, h -> testArrayMisalignedAccess(bbs, h), - false)); + if (bbs.s.isDirect()) { + cases.add(new VarHandleSourceAccessTestCase( + "misaligned access", bav, vh, h -> testArrayMisalignedAccess(bbs, h), + false)); + } } } } @@ -243,122 +284,6 @@ public class VarHandleTestByteArrayAsInt extends VarHandleBaseByteArrayTest { checkNPE(() -> { vh.set(array, ci, VALUE_1); }); - - checkNPE(() -> { - int x = (int) vh.getVolatile(array, ci); - }); - - checkNPE(() -> { - int x = (int) vh.getAcquire(array, ci); - }); - - checkNPE(() -> { - int x = (int) vh.getOpaque(array, ci); - }); - - checkNPE(() -> { - vh.setVolatile(array, ci, VALUE_1); - }); - - checkNPE(() -> { - vh.setRelease(array, ci, VALUE_1); - }); - - checkNPE(() -> { - vh.setOpaque(array, ci, VALUE_1); - }); - - checkNPE(() -> { - boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); - }); - - checkNPE(() -> { - int r = (int) vh.compareAndExchange(array, ci, VALUE_2, VALUE_1); - }); - - checkNPE(() -> { - int r = (int) vh.compareAndExchangeAcquire(array, ci, VALUE_2, VALUE_1); - }); - - checkNPE(() -> { - int r = (int) vh.compareAndExchangeRelease(array, ci, VALUE_2, VALUE_1); - }); - - checkNPE(() -> { - boolean r = vh.weakCompareAndSetPlain(array, ci, VALUE_1, VALUE_2); - }); - - checkNPE(() -> { - boolean r = vh.weakCompareAndSet(array, ci, VALUE_1, VALUE_2); - }); - - checkNPE(() -> { - boolean r = vh.weakCompareAndSetAcquire(array, ci, VALUE_1, VALUE_2); - }); - - checkNPE(() -> { - boolean r = vh.weakCompareAndSetRelease(array, ci, VALUE_1, VALUE_2); - }); - - checkNPE(() -> { - int o = (int) vh.getAndSet(array, ci, VALUE_1); - }); - - checkNPE(() -> { - int o = (int) vh.getAndSetAcquire(array, ci, VALUE_1); - }); - - checkNPE(() -> { - int o = (int) vh.getAndSetRelease(array, ci, VALUE_1); - }); - - checkNPE(() -> { - int o = (int) vh.getAndAdd(array, ci, VALUE_1); - }); - - checkNPE(() -> { - int o = (int) vh.getAndAddAcquire(array, ci, VALUE_1); - }); - - checkNPE(() -> { - int o = (int) vh.getAndAddRelease(array, ci, VALUE_1); - }); - - checkNPE(() -> { - int o = (int) vh.getAndBitwiseOr(array, ci, VALUE_1); - }); - - checkNPE(() -> { - int o = (int) vh.getAndBitwiseOrAcquire(array, ci, VALUE_1); - }); - - checkNPE(() -> { - int o = (int) vh.getAndBitwiseOrRelease(array, ci, VALUE_1); - }); - - checkNPE(() -> { - int o = (int) vh.getAndBitwiseAnd(array, ci, VALUE_1); - }); - - checkNPE(() -> { - int o = (int) vh.getAndBitwiseAndAcquire(array, ci, VALUE_1); - }); - - checkNPE(() -> { - int o = (int) vh.getAndBitwiseAndRelease(array, ci, VALUE_1); - }); - - checkNPE(() -> { - int o = (int) vh.getAndBitwiseXor(array, ci, VALUE_1); - }); - - checkNPE(() -> { - int o = (int) vh.getAndBitwiseXorAcquire(array, ci, VALUE_1); - }); - - checkNPE(() -> { - int o = (int) vh.getAndBitwiseXorRelease(array, ci, VALUE_1); - }); } static void testArrayNPE(ByteBufferSource bs, VarHandleSource vhs) { @@ -496,8 +421,97 @@ public class VarHandleTestByteArrayAsInt extends VarHandleBaseByteArrayTest { byte[] array = bs.s; int ci = 1; + checkUOE(() -> { + boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); + }); + checkUOE(() -> { + int r = (int) vh.compareAndExchange(array, ci, VALUE_2, VALUE_1); + }); + checkUOE(() -> { + int r = (int) vh.compareAndExchangeAcquire(array, ci, VALUE_2, VALUE_1); + }); + + checkUOE(() -> { + int r = (int) vh.compareAndExchangeRelease(array, ci, VALUE_2, VALUE_1); + }); + + checkUOE(() -> { + boolean r = vh.weakCompareAndSetPlain(array, ci, VALUE_1, VALUE_2); + }); + + checkUOE(() -> { + boolean r = vh.weakCompareAndSet(array, ci, VALUE_1, VALUE_2); + }); + + checkUOE(() -> { + boolean r = vh.weakCompareAndSetAcquire(array, ci, VALUE_1, VALUE_2); + }); + + checkUOE(() -> { + boolean r = vh.weakCompareAndSetRelease(array, ci, VALUE_1, VALUE_2); + }); + + checkUOE(() -> { + int o = (int) vh.getAndSet(array, ci, VALUE_1); + }); + + checkUOE(() -> { + int o = (int) vh.getAndSetAcquire(array, ci, VALUE_1); + }); + + checkUOE(() -> { + int o = (int) vh.getAndSetRelease(array, ci, VALUE_1); + }); + + checkUOE(() -> { + int o = (int) vh.getAndAdd(array, ci, VALUE_1); + }); + + checkUOE(() -> { + int o = (int) vh.getAndAddAcquire(array, ci, VALUE_1); + }); + + checkUOE(() -> { + int o = (int) vh.getAndAddRelease(array, ci, VALUE_1); + }); + + checkUOE(() -> { + int o = (int) vh.getAndBitwiseOr(array, ci, VALUE_1); + }); + + checkUOE(() -> { + int o = (int) vh.getAndBitwiseOrAcquire(array, ci, VALUE_1); + }); + + checkUOE(() -> { + int o = (int) vh.getAndBitwiseOrRelease(array, ci, VALUE_1); + }); + + checkUOE(() -> { + int o = (int) vh.getAndBitwiseAnd(array, ci, VALUE_1); + }); + + checkUOE(() -> { + int o = (int) vh.getAndBitwiseAndAcquire(array, ci, VALUE_1); + }); + + checkUOE(() -> { + int o = (int) vh.getAndBitwiseAndRelease(array, ci, VALUE_1); + }); + + checkUOE(() -> { + int o = (int) vh.getAndBitwiseXor(array, ci, VALUE_1); + }); + + checkUOE(() -> { + int o = (int) vh.getAndBitwiseXorAcquire(array, ci, VALUE_1); + }); + + checkUOE(() -> { + int o = (int) vh.getAndBitwiseXorRelease(array, ci, VALUE_1); + }); } static void testArrayUnsupported(ByteBufferSource bs, VarHandleSource vhs) { @@ -512,7 +526,7 @@ public class VarHandleTestByteArrayAsInt extends VarHandleBaseByteArrayTest { }); } - if (readOnly) { + if (readOnly && array.isDirect()) { checkROBE(() -> { vh.setVolatile(array, ci, VALUE_1); }); @@ -524,7 +538,6 @@ public class VarHandleTestByteArrayAsInt extends VarHandleBaseByteArrayTest { checkROBE(() -> { vh.setOpaque(array, ci, VALUE_1); }); - checkROBE(() -> { boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); }); @@ -569,7 +582,6 @@ public class VarHandleTestByteArrayAsInt extends VarHandleBaseByteArrayTest { int o = (int) vh.getAndSetRelease(array, ci, VALUE_1); }); - checkROBE(() -> { int o = (int) vh.getAndAdd(array, ci, VALUE_1); }); @@ -618,7 +630,109 @@ public class VarHandleTestByteArrayAsInt extends VarHandleBaseByteArrayTest { int o = (int) vh.getAndBitwiseXorRelease(array, ci, VALUE_1); }); } - else { + + if (array.isDirect()) { + } else { + checkISE(() -> { + vh.setVolatile(array, ci, VALUE_1); + }); + + checkISE(() -> { + vh.setRelease(array, ci, VALUE_1); + }); + + checkISE(() -> { + vh.setOpaque(array, ci, VALUE_1); + }); + checkISE(() -> { + boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); + }); + + checkISE(() -> { + int r = (int) vh.compareAndExchange(array, ci, VALUE_2, VALUE_1); + }); + + checkISE(() -> { + int r = (int) vh.compareAndExchangeAcquire(array, ci, VALUE_2, VALUE_1); + }); + + checkISE(() -> { + int r = (int) vh.compareAndExchangeRelease(array, ci, VALUE_2, VALUE_1); + }); + + checkISE(() -> { + boolean r = vh.weakCompareAndSetPlain(array, ci, VALUE_1, VALUE_2); + }); + + checkISE(() -> { + boolean r = vh.weakCompareAndSet(array, ci, VALUE_1, VALUE_2); + }); + + checkISE(() -> { + boolean r = vh.weakCompareAndSetAcquire(array, ci, VALUE_1, VALUE_2); + }); + + checkISE(() -> { + boolean r = vh.weakCompareAndSetRelease(array, ci, VALUE_1, VALUE_2); + }); + + checkISE(() -> { + int o = (int) vh.getAndSet(array, ci, VALUE_1); + }); + + checkISE(() -> { + int o = (int) vh.getAndSetAcquire(array, ci, VALUE_1); + }); + + checkISE(() -> { + int o = (int) vh.getAndSetRelease(array, ci, VALUE_1); + }); + checkISE(() -> { + int o = (int) vh.getAndAdd(array, ci, VALUE_1); + }); + + checkISE(() -> { + int o = (int) vh.getAndAddAcquire(array, ci, VALUE_1); + }); + + checkISE(() -> { + int o = (int) vh.getAndAddRelease(array, ci, VALUE_1); + }); + checkISE(() -> { + int o = (int) vh.getAndBitwiseOr(array, ci, VALUE_1); + }); + + checkISE(() -> { + int o = (int) vh.getAndBitwiseOrAcquire(array, ci, VALUE_1); + }); + + checkISE(() -> { + int o = (int) vh.getAndBitwiseOrRelease(array, ci, VALUE_1); + }); + + checkISE(() -> { + int o = (int) vh.getAndBitwiseAnd(array, ci, VALUE_1); + }); + + checkISE(() -> { + int o = (int) vh.getAndBitwiseAndAcquire(array, ci, VALUE_1); + }); + + checkISE(() -> { + int o = (int) vh.getAndBitwiseAndRelease(array, ci, VALUE_1); + }); + + checkISE(() -> { + int o = (int) vh.getAndBitwiseXor(array, ci, VALUE_1); + }); + + checkISE(() -> { + int o = (int) vh.getAndBitwiseXorAcquire(array, ci, VALUE_1); + }); + + checkISE(() -> { + int o = (int) vh.getAndBitwiseXorRelease(array, ci, VALUE_1); + }); } } @@ -638,123 +752,6 @@ public class VarHandleTestByteArrayAsInt extends VarHandleBaseByteArrayTest { checkAIOOBE(() -> { vh.set(array, ci, VALUE_1); }); - - checkAIOOBE(() -> { - int x = (int) vh.getVolatile(array, ci); - }); - - checkAIOOBE(() -> { - int x = (int) vh.getAcquire(array, ci); - }); - - checkAIOOBE(() -> { - int x = (int) vh.getOpaque(array, ci); - }); - - checkAIOOBE(() -> { - vh.setVolatile(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - vh.setRelease(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - vh.setOpaque(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); - }); - - checkAIOOBE(() -> { - int r = (int) vh.compareAndExchange(array, ci, VALUE_2, VALUE_1); - }); - - checkAIOOBE(() -> { - int r = (int) vh.compareAndExchangeAcquire(array, ci, VALUE_2, VALUE_1); - }); - - checkAIOOBE(() -> { - int r = (int) vh.compareAndExchangeRelease(array, ci, VALUE_2, VALUE_1); - }); - - checkAIOOBE(() -> { - boolean r = vh.weakCompareAndSetPlain(array, ci, VALUE_1, VALUE_2); - }); - - checkAIOOBE(() -> { - boolean r = vh.weakCompareAndSet(array, ci, VALUE_1, VALUE_2); - }); - - checkAIOOBE(() -> { - boolean r = vh.weakCompareAndSetAcquire(array, ci, VALUE_1, VALUE_2); - }); - - checkAIOOBE(() -> { - boolean r = vh.weakCompareAndSetRelease(array, ci, VALUE_1, VALUE_2); - }); - - checkAIOOBE(() -> { - int o = (int) vh.getAndSet(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - int o = (int) vh.getAndSetAcquire(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - int o = (int) vh.getAndSetRelease(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - int o = (int) vh.getAndAdd(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - int o = (int) vh.getAndAddAcquire(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - int o = (int) vh.getAndAddRelease(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - int o = (int) vh.getAndBitwiseOr(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - int o = (int) vh.getAndBitwiseOrAcquire(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - int o = (int) vh.getAndBitwiseOrRelease(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - int o = (int) vh.getAndBitwiseAnd(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - int o = (int) vh.getAndBitwiseAndAcquire(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - int o = (int) vh.getAndBitwiseAndRelease(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - int o = (int) vh.getAndBitwiseXor(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - int o = (int) vh.getAndBitwiseXorAcquire(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - int o = (int) vh.getAndBitwiseXorRelease(array, ci, VALUE_1); - }); - } } @@ -778,253 +775,124 @@ public class VarHandleTestByteArrayAsInt extends VarHandleBaseByteArrayTest { }); } - checkIOOBE(() -> { - int x = (int) vh.getVolatile(array, ci); - }); - - checkIOOBE(() -> { - int x = (int) vh.getAcquire(array, ci); - }); - - checkIOOBE(() -> { - int x = (int) vh.getOpaque(array, ci); - }); - - if (!readOnly) { + if (array.isDirect()) { checkIOOBE(() -> { - vh.setVolatile(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - vh.setRelease(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - vh.setOpaque(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); - }); - - checkIOOBE(() -> { - int r = (int) vh.compareAndExchange(array, ci, VALUE_2, VALUE_1); - }); - - checkIOOBE(() -> { - int r = (int) vh.compareAndExchangeAcquire(array, ci, VALUE_2, VALUE_1); - }); - - checkIOOBE(() -> { - int r = (int) vh.compareAndExchangeRelease(array, ci, VALUE_2, VALUE_1); - }); - - checkIOOBE(() -> { - boolean r = vh.weakCompareAndSetPlain(array, ci, VALUE_1, VALUE_2); - }); - - checkIOOBE(() -> { - boolean r = vh.weakCompareAndSet(array, ci, VALUE_1, VALUE_2); - }); - - checkIOOBE(() -> { - boolean r = vh.weakCompareAndSetAcquire(array, ci, VALUE_1, VALUE_2); - }); - - checkIOOBE(() -> { - boolean r = vh.weakCompareAndSetRelease(array, ci, VALUE_1, VALUE_2); - }); - - checkIOOBE(() -> { - int o = (int) vh.getAndSet(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - int o = (int) vh.getAndSetAcquire(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - int o = (int) vh.getAndSetRelease(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - int o = (int) vh.getAndAdd(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - int o = (int) vh.getAndAddAcquire(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - int o = (int) vh.getAndAddRelease(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - int o = (int) vh.getAndBitwiseOr(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - int o = (int) vh.getAndBitwiseOrAcquire(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - int o = (int) vh.getAndBitwiseOrRelease(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - int o = (int) vh.getAndBitwiseAnd(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - int o = (int) vh.getAndBitwiseAndAcquire(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - int o = (int) vh.getAndBitwiseAndRelease(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - int o = (int) vh.getAndBitwiseXor(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - int o = (int) vh.getAndBitwiseXorAcquire(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - int o = (int) vh.getAndBitwiseXorRelease(array, ci, VALUE_1); - }); - } - } - } - - static void testArrayMisalignedAccess(ByteArraySource bs, VarHandleSource vhs) throws Throwable { - VarHandle vh = vhs.s; - byte[] array = bs.s; - - int misalignmentAtZero = ByteBuffer.wrap(array).alignmentOffset(0, SIZE); - - int length = array.length - SIZE + 1; - for (int i = 0; i < length; i++) { - boolean iAligned = ((i + misalignmentAtZero) & (SIZE - 1)) == 0; - final int ci = i; - - if (!iAligned) { - checkISE(() -> { int x = (int) vh.getVolatile(array, ci); }); - checkISE(() -> { + checkIOOBE(() -> { int x = (int) vh.getAcquire(array, ci); }); - checkISE(() -> { + checkIOOBE(() -> { int x = (int) vh.getOpaque(array, ci); }); - checkISE(() -> { - vh.setVolatile(array, ci, VALUE_1); - }); + if (!readOnly) { + checkIOOBE(() -> { + vh.setVolatile(array, ci, VALUE_1); + }); - checkISE(() -> { - vh.setRelease(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + vh.setRelease(array, ci, VALUE_1); + }); - checkISE(() -> { - vh.setOpaque(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + vh.setOpaque(array, ci, VALUE_1); + }); - checkISE(() -> { - boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); - }); + checkIOOBE(() -> { + boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); + }); - checkISE(() -> { - int r = (int) vh.compareAndExchange(array, ci, VALUE_2, VALUE_1); - }); + checkIOOBE(() -> { + int r = (int) vh.compareAndExchange(array, ci, VALUE_2, VALUE_1); + }); - checkISE(() -> { - int r = (int) vh.compareAndExchangeAcquire(array, ci, VALUE_2, VALUE_1); - }); + checkIOOBE(() -> { + int r = (int) vh.compareAndExchangeAcquire(array, ci, VALUE_2, VALUE_1); + }); - checkISE(() -> { - int r = (int) vh.compareAndExchangeRelease(array, ci, VALUE_2, VALUE_1); - }); + checkIOOBE(() -> { + int r = (int) vh.compareAndExchangeRelease(array, ci, VALUE_2, VALUE_1); + }); - checkISE(() -> { - boolean r = vh.weakCompareAndSetPlain(array, ci, VALUE_1, VALUE_2); - }); + checkIOOBE(() -> { + boolean r = vh.weakCompareAndSetPlain(array, ci, VALUE_1, VALUE_2); + }); - checkISE(() -> { - boolean r = vh.weakCompareAndSet(array, ci, VALUE_1, VALUE_2); - }); + checkIOOBE(() -> { + boolean r = vh.weakCompareAndSet(array, ci, VALUE_1, VALUE_2); + }); - checkISE(() -> { - boolean r = vh.weakCompareAndSetAcquire(array, ci, VALUE_1, VALUE_2); - }); + checkIOOBE(() -> { + boolean r = vh.weakCompareAndSetAcquire(array, ci, VALUE_1, VALUE_2); + }); - checkISE(() -> { - boolean r = vh.weakCompareAndSetRelease(array, ci, VALUE_1, VALUE_2); - }); + checkIOOBE(() -> { + boolean r = vh.weakCompareAndSetRelease(array, ci, VALUE_1, VALUE_2); + }); - checkISE(() -> { - int o = (int) vh.getAndSet(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + int o = (int) vh.getAndSet(array, ci, VALUE_1); + }); - checkISE(() -> { - int o = (int) vh.getAndSetAcquire(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + int o = (int) vh.getAndSetAcquire(array, ci, VALUE_1); + }); - checkISE(() -> { - int o = (int) vh.getAndSetRelease(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + int o = (int) vh.getAndSetRelease(array, ci, VALUE_1); + }); - checkISE(() -> { - int o = (int) vh.getAndAdd(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + int o = (int) vh.getAndAdd(array, ci, VALUE_1); + }); - checkISE(() -> { - int o = (int) vh.getAndAddAcquire(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + int o = (int) vh.getAndAddAcquire(array, ci, VALUE_1); + }); - checkISE(() -> { - int o = (int) vh.getAndAddRelease(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + int o = (int) vh.getAndAddRelease(array, ci, VALUE_1); + }); - checkISE(() -> { - int o = (int) vh.getAndBitwiseOr(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + int o = (int) vh.getAndBitwiseOr(array, ci, VALUE_1); + }); - checkISE(() -> { - int o = (int) vh.getAndBitwiseOrAcquire(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + int o = (int) vh.getAndBitwiseOrAcquire(array, ci, VALUE_1); + }); - checkISE(() -> { - int o = (int) vh.getAndBitwiseOrRelease(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + int o = (int) vh.getAndBitwiseOrRelease(array, ci, VALUE_1); + }); - checkISE(() -> { - int o = (int) vh.getAndBitwiseAnd(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + int o = (int) vh.getAndBitwiseAnd(array, ci, VALUE_1); + }); - checkISE(() -> { - int o = (int) vh.getAndBitwiseAndAcquire(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + int o = (int) vh.getAndBitwiseAndAcquire(array, ci, VALUE_1); + }); - checkISE(() -> { - int o = (int) vh.getAndBitwiseAndRelease(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + int o = (int) vh.getAndBitwiseAndRelease(array, ci, VALUE_1); + }); - checkISE(() -> { - int o = (int) vh.getAndBitwiseXor(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + int o = (int) vh.getAndBitwiseXor(array, ci, VALUE_1); + }); - checkISE(() -> { - int o = (int) vh.getAndBitwiseXorAcquire(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + int o = (int) vh.getAndBitwiseXorAcquire(array, ci, VALUE_1); + }); - checkISE(() -> { - int o = (int) vh.getAndBitwiseXorRelease(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + int o = (int) vh.getAndBitwiseXorRelease(array, ci, VALUE_1); + }); + } } } } @@ -1066,7 +934,6 @@ public class VarHandleTestByteArrayAsInt extends VarHandleBaseByteArrayTest { checkISE(() -> { vh.setOpaque(array, ci, VALUE_1); }); - checkISE(() -> { boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); }); @@ -1110,7 +977,6 @@ public class VarHandleTestByteArrayAsInt extends VarHandleBaseByteArrayTest { checkISE(() -> { int o = (int) vh.getAndSetRelease(array, ci, VALUE_1); }); - checkISE(() -> { int o = (int) vh.getAndAdd(array, ci, VALUE_1); }); @@ -1122,7 +988,6 @@ public class VarHandleTestByteArrayAsInt extends VarHandleBaseByteArrayTest { checkISE(() -> { int o = (int) vh.getAndAddRelease(array, ci, VALUE_1); }); - checkISE(() -> { int o = (int) vh.getAndBitwiseOr(array, ci, VALUE_1); }); @@ -1167,314 +1032,15 @@ public class VarHandleTestByteArrayAsInt extends VarHandleBaseByteArrayTest { VarHandle vh = vhs.s; byte[] array = bs.s; - int misalignmentAtZero = ByteBuffer.wrap(array).alignmentOffset(0, SIZE); - bs.fill((byte) 0xff); int length = array.length - SIZE + 1; for (int i = 0; i < length; i++) { - boolean iAligned = ((i + misalignmentAtZero) & (SIZE - 1)) == 0; - // Plain { vh.set(array, i, VALUE_1); int x = (int) vh.get(array, i); assertEquals(x, VALUE_1, "get int value"); } - - - if (iAligned) { - // Volatile - { - vh.setVolatile(array, i, VALUE_2); - int x = (int) vh.getVolatile(array, i); - assertEquals(x, VALUE_2, "setVolatile int value"); - } - - // Lazy - { - vh.setRelease(array, i, VALUE_1); - int x = (int) vh.getAcquire(array, i); - assertEquals(x, VALUE_1, "setRelease int value"); - } - - // Opaque - { - vh.setOpaque(array, i, VALUE_2); - int x = (int) vh.getOpaque(array, i); - assertEquals(x, VALUE_2, "setOpaque int value"); - } - - vh.set(array, i, VALUE_1); - - // Compare - { - boolean r = vh.compareAndSet(array, i, VALUE_1, VALUE_2); - assertEquals(r, true, "success compareAndSet int"); - int x = (int) vh.get(array, i); - assertEquals(x, VALUE_2, "success compareAndSet int value"); - } - - { - boolean r = vh.compareAndSet(array, i, VALUE_1, VALUE_3); - assertEquals(r, false, "failing compareAndSet int"); - int x = (int) vh.get(array, i); - assertEquals(x, VALUE_2, "failing compareAndSet int value"); - } - - { - int r = (int) vh.compareAndExchange(array, i, VALUE_2, VALUE_1); - assertEquals(r, VALUE_2, "success compareAndExchange int"); - int x = (int) vh.get(array, i); - assertEquals(x, VALUE_1, "success compareAndExchange int value"); - } - - { - int r = (int) vh.compareAndExchange(array, i, VALUE_2, VALUE_3); - assertEquals(r, VALUE_1, "failing compareAndExchange int"); - int x = (int) vh.get(array, i); - assertEquals(x, VALUE_1, "failing compareAndExchange int value"); - } - - { - int r = (int) vh.compareAndExchangeAcquire(array, i, VALUE_1, VALUE_2); - assertEquals(r, VALUE_1, "success compareAndExchangeAcquire int"); - int x = (int) vh.get(array, i); - assertEquals(x, VALUE_2, "success compareAndExchangeAcquire int value"); - } - - { - int r = (int) vh.compareAndExchangeAcquire(array, i, VALUE_1, VALUE_3); - assertEquals(r, VALUE_2, "failing compareAndExchangeAcquire int"); - int x = (int) vh.get(array, i); - assertEquals(x, VALUE_2, "failing compareAndExchangeAcquire int value"); - } - - { - int r = (int) vh.compareAndExchangeRelease(array, i, VALUE_2, VALUE_1); - assertEquals(r, VALUE_2, "success compareAndExchangeRelease int"); - int x = (int) vh.get(array, i); - assertEquals(x, VALUE_1, "success compareAndExchangeRelease int value"); - } - - { - int r = (int) vh.compareAndExchangeRelease(array, i, VALUE_2, VALUE_3); - assertEquals(r, VALUE_1, "failing compareAndExchangeRelease int"); - int x = (int) vh.get(array, i); - assertEquals(x, VALUE_1, "failing compareAndExchangeRelease int value"); - } - - { - boolean success = false; - for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) { - success = vh.weakCompareAndSetPlain(array, i, VALUE_1, VALUE_2); - if (!success) weakDelay(); - } - assertEquals(success, true, "success weakCompareAndSetPlain int"); - int x = (int) vh.get(array, i); - assertEquals(x, VALUE_2, "success weakCompareAndSetPlain int value"); - } - - { - boolean success = vh.weakCompareAndSetPlain(array, i, VALUE_1, VALUE_3); - assertEquals(success, false, "failing weakCompareAndSetPlain int"); - int x = (int) vh.get(array, i); - assertEquals(x, VALUE_2, "failing weakCompareAndSetPlain int value"); - } - - { - boolean success = false; - for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) { - success = vh.weakCompareAndSetAcquire(array, i, VALUE_2, VALUE_1); - if (!success) weakDelay(); - } - assertEquals(success, true, "success weakCompareAndSetAcquire int"); - int x = (int) vh.get(array, i); - assertEquals(x, VALUE_1, "success weakCompareAndSetAcquire int"); - } - - { - boolean success = vh.weakCompareAndSetAcquire(array, i, VALUE_2, VALUE_3); - assertEquals(success, false, "failing weakCompareAndSetAcquire int"); - int x = (int) vh.get(array, i); - assertEquals(x, VALUE_1, "failing weakCompareAndSetAcquire int value"); - } - - { - boolean success = false; - for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) { - success = vh.weakCompareAndSetRelease(array, i, VALUE_1, VALUE_2); - if (!success) weakDelay(); - } - assertEquals(success, true, "success weakCompareAndSetRelease int"); - int x = (int) vh.get(array, i); - assertEquals(x, VALUE_2, "success weakCompareAndSetRelease int"); - } - - { - boolean success = vh.weakCompareAndSetRelease(array, i, VALUE_1, VALUE_3); - assertEquals(success, false, "failing weakCompareAndSetRelease int"); - int x = (int) vh.get(array, i); - assertEquals(x, VALUE_2, "failing weakCompareAndSetRelease int value"); - } - - { - boolean success = false; - for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) { - success = vh.weakCompareAndSet(array, i, VALUE_2, VALUE_1); - if (!success) weakDelay(); - } - assertEquals(success, true, "success weakCompareAndSet int"); - int x = (int) vh.get(array, i); - assertEquals(x, VALUE_1, "success weakCompareAndSet int"); - } - - { - boolean success = vh.weakCompareAndSet(array, i, VALUE_2, VALUE_3); - assertEquals(success, false, "failing weakCompareAndSet int"); - int x = (int) vh.get(array, i); - assertEquals(x, VALUE_1, "failing weakCompareAndSet int value"); - } - - // Compare set and get - { - vh.set(array, i, VALUE_1); - - int o = (int) vh.getAndSet(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndSet int"); - int x = (int) vh.get(array, i); - assertEquals(x, VALUE_2, "getAndSet int value"); - } - - { - vh.set(array, i, VALUE_1); - - int o = (int) vh.getAndSetAcquire(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndSetAcquire int"); - int x = (int) vh.get(array, i); - assertEquals(x, VALUE_2, "getAndSetAcquire int value"); - } - - { - vh.set(array, i, VALUE_1); - - int o = (int) vh.getAndSetRelease(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndSetRelease int"); - int x = (int) vh.get(array, i); - assertEquals(x, VALUE_2, "getAndSetRelease int value"); - } - - // get and add, add and get - { - vh.set(array, i, VALUE_1); - - int o = (int) vh.getAndAdd(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndAdd int"); - int x = (int) vh.get(array, i); - assertEquals(x, VALUE_1 + VALUE_2, "getAndAdd int value"); - } - - { - vh.set(array, i, VALUE_1); - - int o = (int) vh.getAndAddAcquire(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndAddAcquire int"); - int x = (int) vh.get(array, i); - assertEquals(x, VALUE_1 + VALUE_2, "getAndAddAcquire int value"); - } - - { - vh.set(array, i, VALUE_1); - - int o = (int) vh.getAndAddRelease(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndAddRelease int"); - int x = (int) vh.get(array, i); - assertEquals(x, VALUE_1 + VALUE_2, "getAndAddRelease int value"); - } - - // get and bitwise or - { - vh.set(array, i, VALUE_1); - - int o = (int) vh.getAndBitwiseOr(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndBitwiseOr int"); - int x = (int) vh.get(array, i); - assertEquals(x, VALUE_1 | VALUE_2, "getAndBitwiseOr int value"); - } - - { - vh.set(array, i, VALUE_1); - - int o = (int) vh.getAndBitwiseOrAcquire(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndBitwiseOrAcquire int"); - int x = (int) vh.get(array, i); - assertEquals(x, VALUE_1 | VALUE_2, "getAndBitwiseOrAcquire int value"); - } - - { - vh.set(array, i, VALUE_1); - - int o = (int) vh.getAndBitwiseOrRelease(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndBitwiseOrRelease int"); - int x = (int) vh.get(array, i); - assertEquals(x, VALUE_1 | VALUE_2, "getAndBitwiseOrRelease int value"); - } - - // get and bitwise and - { - vh.set(array, i, VALUE_1); - - int o = (int) vh.getAndBitwiseAnd(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndBitwiseAnd int"); - int x = (int) vh.get(array, i); - assertEquals(x, VALUE_1 & VALUE_2, "getAndBitwiseAnd int value"); - } - - { - vh.set(array, i, VALUE_1); - - int o = (int) vh.getAndBitwiseAndAcquire(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndBitwiseAndAcquire int"); - int x = (int) vh.get(array, i); - assertEquals(x, VALUE_1 & VALUE_2, "getAndBitwiseAndAcquire int value"); - } - - { - vh.set(array, i, VALUE_1); - - int o = (int) vh.getAndBitwiseAndRelease(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndBitwiseAndRelease int"); - int x = (int) vh.get(array, i); - assertEquals(x, VALUE_1 & VALUE_2, "getAndBitwiseAndRelease int value"); - } - - // get and bitwise xor - { - vh.set(array, i, VALUE_1); - - int o = (int) vh.getAndBitwiseXor(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndBitwiseXor int"); - int x = (int) vh.get(array, i); - assertEquals(x, VALUE_1 ^ VALUE_2, "getAndBitwiseXor int value"); - } - - { - vh.set(array, i, VALUE_1); - - int o = (int) vh.getAndBitwiseXorAcquire(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndBitwiseXorAcquire int"); - int x = (int) vh.get(array, i); - assertEquals(x, VALUE_1 ^ VALUE_2, "getAndBitwiseXorAcquire int value"); - } - - { - vh.set(array, i, VALUE_1); - - int o = (int) vh.getAndBitwiseXorRelease(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndBitwiseXorRelease int"); - int x = (int) vh.get(array, i); - assertEquals(x, VALUE_1 ^ VALUE_2, "getAndBitwiseXorRelease int value"); - } - } } } @@ -1483,12 +1049,10 @@ public class VarHandleTestByteArrayAsInt extends VarHandleBaseByteArrayTest { VarHandle vh = vhs.s; ByteBuffer array = bs.s; - int misalignmentAtZero = array.alignmentOffset(0, SIZE); - bs.fill((byte) 0xff); int length = array.limit() - SIZE + 1; for (int i = 0; i < length; i++) { - boolean iAligned = ((i + misalignmentAtZero) & (SIZE - 1)) == 0; + boolean iAligned = array.isDirect() ? ((i + array.alignmentOffset(0, SIZE)) & (SIZE - 1)) == 0 : false; // Plain { @@ -1797,15 +1361,13 @@ public class VarHandleTestByteArrayAsInt extends VarHandleBaseByteArrayTest { VarHandle vh = vhs.s; ByteBuffer array = bs.s; - int misalignmentAtZero = array.alignmentOffset(0, SIZE); - ByteBuffer bb = ByteBuffer.allocate(SIZE); bb.order(MemoryMode.BIG_ENDIAN.isSet(vhs.memoryModes) ? ByteOrder.BIG_ENDIAN : ByteOrder.LITTLE_ENDIAN); bs.fill(bb.putInt(0, VALUE_2).array()); int length = array.limit() - SIZE + 1; for (int i = 0; i < length; i++) { - boolean iAligned = ((i + misalignmentAtZero) & (SIZE - 1)) == 0; + boolean iAligned = array.isDirect() ? ((i + array.alignmentOffset(0, SIZE)) & (SIZE - 1)) == 0 : false; int v = MemoryMode.BIG_ENDIAN.isSet(vhs.memoryModes) ? rotateLeft(VALUE_2, (i % SIZE) << 3) diff --git a/test/jdk/java/lang/invoke/VarHandles/VarHandleTestByteArrayAsLong.java b/test/jdk/java/lang/invoke/VarHandles/VarHandleTestByteArrayAsLong.java index d13bb1c03df..8324a488035 100644 --- a/test/jdk/java/lang/invoke/VarHandles/VarHandleTestByteArrayAsLong.java +++ b/test/jdk/java/lang/invoke/VarHandles/VarHandleTestByteArrayAsLong.java @@ -72,12 +72,12 @@ public class VarHandleTestByteArrayAsLong extends VarHandleBaseByteArrayTest { arrayType = int[].class; } VarHandleSource aeh = new VarHandleSource( - MethodHandles.byteArrayViewVarHandle(arrayType, bo), + MethodHandles.byteArrayViewVarHandle(arrayType, bo), false, endianess, MemoryMode.READ_WRITE); vhss.add(aeh); VarHandleSource bbh = new VarHandleSource( - MethodHandles.byteBufferViewVarHandle(arrayType, bo), + MethodHandles.byteBufferViewVarHandle(arrayType, bo), true, endianess, MemoryMode.READ_WRITE); vhss.add(bbh); } @@ -114,38 +114,80 @@ public class VarHandleTestByteArrayAsLong extends VarHandleBaseByteArrayTest { assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET)); assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_VOLATILE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_VOLATILE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_ACQUIRE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_RELEASE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_OPAQUE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_OPAQUE)); + if (vhs.supportsAtomicAccess) { + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_VOLATILE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_VOLATILE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_ACQUIRE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_RELEASE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_OPAQUE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_OPAQUE)); + } else { + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_VOLATILE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.SET_VOLATILE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.SET_RELEASE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_OPAQUE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.SET_OPAQUE)); + } - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_SET)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_ACQUIRE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_RELEASE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_PLAIN)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_ACQUIRE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_RELEASE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET_ACQUIRE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET_RELEASE)); + if (vhs.supportsAtomicAccess) { + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_SET)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_ACQUIRE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_RELEASE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_PLAIN)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_ACQUIRE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_RELEASE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET_ACQUIRE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET_RELEASE)); + } else { + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_SET)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_RELEASE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_PLAIN)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_RELEASE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET_RELEASE)); + } - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD_ACQUIRE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD_RELEASE)); + if (vhs.supportsAtomicAccess) { + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD_ACQUIRE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD_RELEASE)); + } else { + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD_RELEASE)); + } - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR_ACQUIRE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR_RELEASE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND_ACQUIRE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND_RELEASE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR_ACQUIRE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR_RELEASE)); + + if (vhs.supportsAtomicAccess) { + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR_ACQUIRE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR_RELEASE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND_ACQUIRE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND_RELEASE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR_ACQUIRE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR_RELEASE)); + } else { + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR_RELEASE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND_RELEASE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR_RELEASE)); + } } @Test(dataProvider = "typesProvider") @@ -180,9 +222,6 @@ public class VarHandleTestByteArrayAsLong extends VarHandleBaseByteArrayTest { cases.add(new VarHandleSourceAccessTestCase( "index out of bounds", bav, vh, h -> testArrayIndexOutOfBounds(bas, h), false)); - cases.add(new VarHandleSourceAccessTestCase( - "misaligned access", bav, vh, h -> testArrayMisalignedAccess(bas, h), - false)); } else { ByteBufferSource bbs = (ByteBufferSource) bav; @@ -207,9 +246,11 @@ public class VarHandleTestByteArrayAsLong extends VarHandleBaseByteArrayTest { cases.add(new VarHandleSourceAccessTestCase( "index out of bounds", bav, vh, h -> testArrayIndexOutOfBounds(bbs, h), false)); - cases.add(new VarHandleSourceAccessTestCase( - "misaligned access", bav, vh, h -> testArrayMisalignedAccess(bbs, h), - false)); + if (bbs.s.isDirect()) { + cases.add(new VarHandleSourceAccessTestCase( + "misaligned access", bav, vh, h -> testArrayMisalignedAccess(bbs, h), + false)); + } } } } @@ -243,122 +284,6 @@ public class VarHandleTestByteArrayAsLong extends VarHandleBaseByteArrayTest { checkNPE(() -> { vh.set(array, ci, VALUE_1); }); - - checkNPE(() -> { - long x = (long) vh.getVolatile(array, ci); - }); - - checkNPE(() -> { - long x = (long) vh.getAcquire(array, ci); - }); - - checkNPE(() -> { - long x = (long) vh.getOpaque(array, ci); - }); - - checkNPE(() -> { - vh.setVolatile(array, ci, VALUE_1); - }); - - checkNPE(() -> { - vh.setRelease(array, ci, VALUE_1); - }); - - checkNPE(() -> { - vh.setOpaque(array, ci, VALUE_1); - }); - - checkNPE(() -> { - boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); - }); - - checkNPE(() -> { - long r = (long) vh.compareAndExchange(array, ci, VALUE_2, VALUE_1); - }); - - checkNPE(() -> { - long r = (long) vh.compareAndExchangeAcquire(array, ci, VALUE_2, VALUE_1); - }); - - checkNPE(() -> { - long r = (long) vh.compareAndExchangeRelease(array, ci, VALUE_2, VALUE_1); - }); - - checkNPE(() -> { - boolean r = vh.weakCompareAndSetPlain(array, ci, VALUE_1, VALUE_2); - }); - - checkNPE(() -> { - boolean r = vh.weakCompareAndSet(array, ci, VALUE_1, VALUE_2); - }); - - checkNPE(() -> { - boolean r = vh.weakCompareAndSetAcquire(array, ci, VALUE_1, VALUE_2); - }); - - checkNPE(() -> { - boolean r = vh.weakCompareAndSetRelease(array, ci, VALUE_1, VALUE_2); - }); - - checkNPE(() -> { - long o = (long) vh.getAndSet(array, ci, VALUE_1); - }); - - checkNPE(() -> { - long o = (long) vh.getAndSetAcquire(array, ci, VALUE_1); - }); - - checkNPE(() -> { - long o = (long) vh.getAndSetRelease(array, ci, VALUE_1); - }); - - checkNPE(() -> { - long o = (long) vh.getAndAdd(array, ci, VALUE_1); - }); - - checkNPE(() -> { - long o = (long) vh.getAndAddAcquire(array, ci, VALUE_1); - }); - - checkNPE(() -> { - long o = (long) vh.getAndAddRelease(array, ci, VALUE_1); - }); - - checkNPE(() -> { - long o = (long) vh.getAndBitwiseOr(array, ci, VALUE_1); - }); - - checkNPE(() -> { - long o = (long) vh.getAndBitwiseOrAcquire(array, ci, VALUE_1); - }); - - checkNPE(() -> { - long o = (long) vh.getAndBitwiseOrRelease(array, ci, VALUE_1); - }); - - checkNPE(() -> { - long o = (long) vh.getAndBitwiseAnd(array, ci, VALUE_1); - }); - - checkNPE(() -> { - long o = (long) vh.getAndBitwiseAndAcquire(array, ci, VALUE_1); - }); - - checkNPE(() -> { - long o = (long) vh.getAndBitwiseAndRelease(array, ci, VALUE_1); - }); - - checkNPE(() -> { - long o = (long) vh.getAndBitwiseXor(array, ci, VALUE_1); - }); - - checkNPE(() -> { - long o = (long) vh.getAndBitwiseXorAcquire(array, ci, VALUE_1); - }); - - checkNPE(() -> { - long o = (long) vh.getAndBitwiseXorRelease(array, ci, VALUE_1); - }); } static void testArrayNPE(ByteBufferSource bs, VarHandleSource vhs) { @@ -496,8 +421,97 @@ public class VarHandleTestByteArrayAsLong extends VarHandleBaseByteArrayTest { byte[] array = bs.s; int ci = 1; + checkUOE(() -> { + boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); + }); + checkUOE(() -> { + long r = (long) vh.compareAndExchange(array, ci, VALUE_2, VALUE_1); + }); + checkUOE(() -> { + long r = (long) vh.compareAndExchangeAcquire(array, ci, VALUE_2, VALUE_1); + }); + + checkUOE(() -> { + long r = (long) vh.compareAndExchangeRelease(array, ci, VALUE_2, VALUE_1); + }); + + checkUOE(() -> { + boolean r = vh.weakCompareAndSetPlain(array, ci, VALUE_1, VALUE_2); + }); + + checkUOE(() -> { + boolean r = vh.weakCompareAndSet(array, ci, VALUE_1, VALUE_2); + }); + + checkUOE(() -> { + boolean r = vh.weakCompareAndSetAcquire(array, ci, VALUE_1, VALUE_2); + }); + + checkUOE(() -> { + boolean r = vh.weakCompareAndSetRelease(array, ci, VALUE_1, VALUE_2); + }); + + checkUOE(() -> { + long o = (long) vh.getAndSet(array, ci, VALUE_1); + }); + + checkUOE(() -> { + long o = (long) vh.getAndSetAcquire(array, ci, VALUE_1); + }); + + checkUOE(() -> { + long o = (long) vh.getAndSetRelease(array, ci, VALUE_1); + }); + + checkUOE(() -> { + long o = (long) vh.getAndAdd(array, ci, VALUE_1); + }); + + checkUOE(() -> { + long o = (long) vh.getAndAddAcquire(array, ci, VALUE_1); + }); + + checkUOE(() -> { + long o = (long) vh.getAndAddRelease(array, ci, VALUE_1); + }); + + checkUOE(() -> { + long o = (long) vh.getAndBitwiseOr(array, ci, VALUE_1); + }); + + checkUOE(() -> { + long o = (long) vh.getAndBitwiseOrAcquire(array, ci, VALUE_1); + }); + + checkUOE(() -> { + long o = (long) vh.getAndBitwiseOrRelease(array, ci, VALUE_1); + }); + + checkUOE(() -> { + long o = (long) vh.getAndBitwiseAnd(array, ci, VALUE_1); + }); + + checkUOE(() -> { + long o = (long) vh.getAndBitwiseAndAcquire(array, ci, VALUE_1); + }); + + checkUOE(() -> { + long o = (long) vh.getAndBitwiseAndRelease(array, ci, VALUE_1); + }); + + checkUOE(() -> { + long o = (long) vh.getAndBitwiseXor(array, ci, VALUE_1); + }); + + checkUOE(() -> { + long o = (long) vh.getAndBitwiseXorAcquire(array, ci, VALUE_1); + }); + + checkUOE(() -> { + long o = (long) vh.getAndBitwiseXorRelease(array, ci, VALUE_1); + }); } static void testArrayUnsupported(ByteBufferSource bs, VarHandleSource vhs) { @@ -512,7 +526,7 @@ public class VarHandleTestByteArrayAsLong extends VarHandleBaseByteArrayTest { }); } - if (readOnly) { + if (readOnly && array.isDirect()) { checkROBE(() -> { vh.setVolatile(array, ci, VALUE_1); }); @@ -524,7 +538,6 @@ public class VarHandleTestByteArrayAsLong extends VarHandleBaseByteArrayTest { checkROBE(() -> { vh.setOpaque(array, ci, VALUE_1); }); - checkROBE(() -> { boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); }); @@ -569,7 +582,6 @@ public class VarHandleTestByteArrayAsLong extends VarHandleBaseByteArrayTest { long o = (long) vh.getAndSetRelease(array, ci, VALUE_1); }); - checkROBE(() -> { long o = (long) vh.getAndAdd(array, ci, VALUE_1); }); @@ -618,7 +630,109 @@ public class VarHandleTestByteArrayAsLong extends VarHandleBaseByteArrayTest { long o = (long) vh.getAndBitwiseXorRelease(array, ci, VALUE_1); }); } - else { + + if (array.isDirect()) { + } else { + checkISE(() -> { + vh.setVolatile(array, ci, VALUE_1); + }); + + checkISE(() -> { + vh.setRelease(array, ci, VALUE_1); + }); + + checkISE(() -> { + vh.setOpaque(array, ci, VALUE_1); + }); + checkISE(() -> { + boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); + }); + + checkISE(() -> { + long r = (long) vh.compareAndExchange(array, ci, VALUE_2, VALUE_1); + }); + + checkISE(() -> { + long r = (long) vh.compareAndExchangeAcquire(array, ci, VALUE_2, VALUE_1); + }); + + checkISE(() -> { + long r = (long) vh.compareAndExchangeRelease(array, ci, VALUE_2, VALUE_1); + }); + + checkISE(() -> { + boolean r = vh.weakCompareAndSetPlain(array, ci, VALUE_1, VALUE_2); + }); + + checkISE(() -> { + boolean r = vh.weakCompareAndSet(array, ci, VALUE_1, VALUE_2); + }); + + checkISE(() -> { + boolean r = vh.weakCompareAndSetAcquire(array, ci, VALUE_1, VALUE_2); + }); + + checkISE(() -> { + boolean r = vh.weakCompareAndSetRelease(array, ci, VALUE_1, VALUE_2); + }); + + checkISE(() -> { + long o = (long) vh.getAndSet(array, ci, VALUE_1); + }); + + checkISE(() -> { + long o = (long) vh.getAndSetAcquire(array, ci, VALUE_1); + }); + + checkISE(() -> { + long o = (long) vh.getAndSetRelease(array, ci, VALUE_1); + }); + checkISE(() -> { + long o = (long) vh.getAndAdd(array, ci, VALUE_1); + }); + + checkISE(() -> { + long o = (long) vh.getAndAddAcquire(array, ci, VALUE_1); + }); + + checkISE(() -> { + long o = (long) vh.getAndAddRelease(array, ci, VALUE_1); + }); + checkISE(() -> { + long o = (long) vh.getAndBitwiseOr(array, ci, VALUE_1); + }); + + checkISE(() -> { + long o = (long) vh.getAndBitwiseOrAcquire(array, ci, VALUE_1); + }); + + checkISE(() -> { + long o = (long) vh.getAndBitwiseOrRelease(array, ci, VALUE_1); + }); + + checkISE(() -> { + long o = (long) vh.getAndBitwiseAnd(array, ci, VALUE_1); + }); + + checkISE(() -> { + long o = (long) vh.getAndBitwiseAndAcquire(array, ci, VALUE_1); + }); + + checkISE(() -> { + long o = (long) vh.getAndBitwiseAndRelease(array, ci, VALUE_1); + }); + + checkISE(() -> { + long o = (long) vh.getAndBitwiseXor(array, ci, VALUE_1); + }); + + checkISE(() -> { + long o = (long) vh.getAndBitwiseXorAcquire(array, ci, VALUE_1); + }); + + checkISE(() -> { + long o = (long) vh.getAndBitwiseXorRelease(array, ci, VALUE_1); + }); } } @@ -638,123 +752,6 @@ public class VarHandleTestByteArrayAsLong extends VarHandleBaseByteArrayTest { checkAIOOBE(() -> { vh.set(array, ci, VALUE_1); }); - - checkAIOOBE(() -> { - long x = (long) vh.getVolatile(array, ci); - }); - - checkAIOOBE(() -> { - long x = (long) vh.getAcquire(array, ci); - }); - - checkAIOOBE(() -> { - long x = (long) vh.getOpaque(array, ci); - }); - - checkAIOOBE(() -> { - vh.setVolatile(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - vh.setRelease(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - vh.setOpaque(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); - }); - - checkAIOOBE(() -> { - long r = (long) vh.compareAndExchange(array, ci, VALUE_2, VALUE_1); - }); - - checkAIOOBE(() -> { - long r = (long) vh.compareAndExchangeAcquire(array, ci, VALUE_2, VALUE_1); - }); - - checkAIOOBE(() -> { - long r = (long) vh.compareAndExchangeRelease(array, ci, VALUE_2, VALUE_1); - }); - - checkAIOOBE(() -> { - boolean r = vh.weakCompareAndSetPlain(array, ci, VALUE_1, VALUE_2); - }); - - checkAIOOBE(() -> { - boolean r = vh.weakCompareAndSet(array, ci, VALUE_1, VALUE_2); - }); - - checkAIOOBE(() -> { - boolean r = vh.weakCompareAndSetAcquire(array, ci, VALUE_1, VALUE_2); - }); - - checkAIOOBE(() -> { - boolean r = vh.weakCompareAndSetRelease(array, ci, VALUE_1, VALUE_2); - }); - - checkAIOOBE(() -> { - long o = (long) vh.getAndSet(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - long o = (long) vh.getAndSetAcquire(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - long o = (long) vh.getAndSetRelease(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - long o = (long) vh.getAndAdd(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - long o = (long) vh.getAndAddAcquire(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - long o = (long) vh.getAndAddRelease(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - long o = (long) vh.getAndBitwiseOr(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - long o = (long) vh.getAndBitwiseOrAcquire(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - long o = (long) vh.getAndBitwiseOrRelease(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - long o = (long) vh.getAndBitwiseAnd(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - long o = (long) vh.getAndBitwiseAndAcquire(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - long o = (long) vh.getAndBitwiseAndRelease(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - long o = (long) vh.getAndBitwiseXor(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - long o = (long) vh.getAndBitwiseXorAcquire(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - long o = (long) vh.getAndBitwiseXorRelease(array, ci, VALUE_1); - }); - } } @@ -778,253 +775,124 @@ public class VarHandleTestByteArrayAsLong extends VarHandleBaseByteArrayTest { }); } - checkIOOBE(() -> { - long x = (long) vh.getVolatile(array, ci); - }); - - checkIOOBE(() -> { - long x = (long) vh.getAcquire(array, ci); - }); - - checkIOOBE(() -> { - long x = (long) vh.getOpaque(array, ci); - }); - - if (!readOnly) { + if (array.isDirect()) { checkIOOBE(() -> { - vh.setVolatile(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - vh.setRelease(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - vh.setOpaque(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); - }); - - checkIOOBE(() -> { - long r = (long) vh.compareAndExchange(array, ci, VALUE_2, VALUE_1); - }); - - checkIOOBE(() -> { - long r = (long) vh.compareAndExchangeAcquire(array, ci, VALUE_2, VALUE_1); - }); - - checkIOOBE(() -> { - long r = (long) vh.compareAndExchangeRelease(array, ci, VALUE_2, VALUE_1); - }); - - checkIOOBE(() -> { - boolean r = vh.weakCompareAndSetPlain(array, ci, VALUE_1, VALUE_2); - }); - - checkIOOBE(() -> { - boolean r = vh.weakCompareAndSet(array, ci, VALUE_1, VALUE_2); - }); - - checkIOOBE(() -> { - boolean r = vh.weakCompareAndSetAcquire(array, ci, VALUE_1, VALUE_2); - }); - - checkIOOBE(() -> { - boolean r = vh.weakCompareAndSetRelease(array, ci, VALUE_1, VALUE_2); - }); - - checkIOOBE(() -> { - long o = (long) vh.getAndSet(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - long o = (long) vh.getAndSetAcquire(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - long o = (long) vh.getAndSetRelease(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - long o = (long) vh.getAndAdd(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - long o = (long) vh.getAndAddAcquire(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - long o = (long) vh.getAndAddRelease(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - long o = (long) vh.getAndBitwiseOr(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - long o = (long) vh.getAndBitwiseOrAcquire(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - long o = (long) vh.getAndBitwiseOrRelease(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - long o = (long) vh.getAndBitwiseAnd(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - long o = (long) vh.getAndBitwiseAndAcquire(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - long o = (long) vh.getAndBitwiseAndRelease(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - long o = (long) vh.getAndBitwiseXor(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - long o = (long) vh.getAndBitwiseXorAcquire(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - long o = (long) vh.getAndBitwiseXorRelease(array, ci, VALUE_1); - }); - } - } - } - - static void testArrayMisalignedAccess(ByteArraySource bs, VarHandleSource vhs) throws Throwable { - VarHandle vh = vhs.s; - byte[] array = bs.s; - - int misalignmentAtZero = ByteBuffer.wrap(array).alignmentOffset(0, SIZE); - - int length = array.length - SIZE + 1; - for (int i = 0; i < length; i++) { - boolean iAligned = ((i + misalignmentAtZero) & (SIZE - 1)) == 0; - final int ci = i; - - if (!iAligned) { - checkISE(() -> { long x = (long) vh.getVolatile(array, ci); }); - checkISE(() -> { + checkIOOBE(() -> { long x = (long) vh.getAcquire(array, ci); }); - checkISE(() -> { + checkIOOBE(() -> { long x = (long) vh.getOpaque(array, ci); }); - checkISE(() -> { - vh.setVolatile(array, ci, VALUE_1); - }); + if (!readOnly) { + checkIOOBE(() -> { + vh.setVolatile(array, ci, VALUE_1); + }); - checkISE(() -> { - vh.setRelease(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + vh.setRelease(array, ci, VALUE_1); + }); - checkISE(() -> { - vh.setOpaque(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + vh.setOpaque(array, ci, VALUE_1); + }); - checkISE(() -> { - boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); - }); + checkIOOBE(() -> { + boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); + }); - checkISE(() -> { - long r = (long) vh.compareAndExchange(array, ci, VALUE_2, VALUE_1); - }); + checkIOOBE(() -> { + long r = (long) vh.compareAndExchange(array, ci, VALUE_2, VALUE_1); + }); - checkISE(() -> { - long r = (long) vh.compareAndExchangeAcquire(array, ci, VALUE_2, VALUE_1); - }); + checkIOOBE(() -> { + long r = (long) vh.compareAndExchangeAcquire(array, ci, VALUE_2, VALUE_1); + }); - checkISE(() -> { - long r = (long) vh.compareAndExchangeRelease(array, ci, VALUE_2, VALUE_1); - }); + checkIOOBE(() -> { + long r = (long) vh.compareAndExchangeRelease(array, ci, VALUE_2, VALUE_1); + }); - checkISE(() -> { - boolean r = vh.weakCompareAndSetPlain(array, ci, VALUE_1, VALUE_2); - }); + checkIOOBE(() -> { + boolean r = vh.weakCompareAndSetPlain(array, ci, VALUE_1, VALUE_2); + }); - checkISE(() -> { - boolean r = vh.weakCompareAndSet(array, ci, VALUE_1, VALUE_2); - }); + checkIOOBE(() -> { + boolean r = vh.weakCompareAndSet(array, ci, VALUE_1, VALUE_2); + }); - checkISE(() -> { - boolean r = vh.weakCompareAndSetAcquire(array, ci, VALUE_1, VALUE_2); - }); + checkIOOBE(() -> { + boolean r = vh.weakCompareAndSetAcquire(array, ci, VALUE_1, VALUE_2); + }); - checkISE(() -> { - boolean r = vh.weakCompareAndSetRelease(array, ci, VALUE_1, VALUE_2); - }); + checkIOOBE(() -> { + boolean r = vh.weakCompareAndSetRelease(array, ci, VALUE_1, VALUE_2); + }); - checkISE(() -> { - long o = (long) vh.getAndSet(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + long o = (long) vh.getAndSet(array, ci, VALUE_1); + }); - checkISE(() -> { - long o = (long) vh.getAndSetAcquire(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + long o = (long) vh.getAndSetAcquire(array, ci, VALUE_1); + }); - checkISE(() -> { - long o = (long) vh.getAndSetRelease(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + long o = (long) vh.getAndSetRelease(array, ci, VALUE_1); + }); - checkISE(() -> { - long o = (long) vh.getAndAdd(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + long o = (long) vh.getAndAdd(array, ci, VALUE_1); + }); - checkISE(() -> { - long o = (long) vh.getAndAddAcquire(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + long o = (long) vh.getAndAddAcquire(array, ci, VALUE_1); + }); - checkISE(() -> { - long o = (long) vh.getAndAddRelease(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + long o = (long) vh.getAndAddRelease(array, ci, VALUE_1); + }); - checkISE(() -> { - long o = (long) vh.getAndBitwiseOr(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + long o = (long) vh.getAndBitwiseOr(array, ci, VALUE_1); + }); - checkISE(() -> { - long o = (long) vh.getAndBitwiseOrAcquire(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + long o = (long) vh.getAndBitwiseOrAcquire(array, ci, VALUE_1); + }); - checkISE(() -> { - long o = (long) vh.getAndBitwiseOrRelease(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + long o = (long) vh.getAndBitwiseOrRelease(array, ci, VALUE_1); + }); - checkISE(() -> { - long o = (long) vh.getAndBitwiseAnd(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + long o = (long) vh.getAndBitwiseAnd(array, ci, VALUE_1); + }); - checkISE(() -> { - long o = (long) vh.getAndBitwiseAndAcquire(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + long o = (long) vh.getAndBitwiseAndAcquire(array, ci, VALUE_1); + }); - checkISE(() -> { - long o = (long) vh.getAndBitwiseAndRelease(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + long o = (long) vh.getAndBitwiseAndRelease(array, ci, VALUE_1); + }); - checkISE(() -> { - long o = (long) vh.getAndBitwiseXor(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + long o = (long) vh.getAndBitwiseXor(array, ci, VALUE_1); + }); - checkISE(() -> { - long o = (long) vh.getAndBitwiseXorAcquire(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + long o = (long) vh.getAndBitwiseXorAcquire(array, ci, VALUE_1); + }); - checkISE(() -> { - long o = (long) vh.getAndBitwiseXorRelease(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + long o = (long) vh.getAndBitwiseXorRelease(array, ci, VALUE_1); + }); + } } } } @@ -1066,7 +934,6 @@ public class VarHandleTestByteArrayAsLong extends VarHandleBaseByteArrayTest { checkISE(() -> { vh.setOpaque(array, ci, VALUE_1); }); - checkISE(() -> { boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); }); @@ -1110,7 +977,6 @@ public class VarHandleTestByteArrayAsLong extends VarHandleBaseByteArrayTest { checkISE(() -> { long o = (long) vh.getAndSetRelease(array, ci, VALUE_1); }); - checkISE(() -> { long o = (long) vh.getAndAdd(array, ci, VALUE_1); }); @@ -1122,7 +988,6 @@ public class VarHandleTestByteArrayAsLong extends VarHandleBaseByteArrayTest { checkISE(() -> { long o = (long) vh.getAndAddRelease(array, ci, VALUE_1); }); - checkISE(() -> { long o = (long) vh.getAndBitwiseOr(array, ci, VALUE_1); }); @@ -1167,314 +1032,15 @@ public class VarHandleTestByteArrayAsLong extends VarHandleBaseByteArrayTest { VarHandle vh = vhs.s; byte[] array = bs.s; - int misalignmentAtZero = ByteBuffer.wrap(array).alignmentOffset(0, SIZE); - bs.fill((byte) 0xff); int length = array.length - SIZE + 1; for (int i = 0; i < length; i++) { - boolean iAligned = ((i + misalignmentAtZero) & (SIZE - 1)) == 0; - // Plain { vh.set(array, i, VALUE_1); long x = (long) vh.get(array, i); assertEquals(x, VALUE_1, "get long value"); } - - - if (iAligned) { - // Volatile - { - vh.setVolatile(array, i, VALUE_2); - long x = (long) vh.getVolatile(array, i); - assertEquals(x, VALUE_2, "setVolatile long value"); - } - - // Lazy - { - vh.setRelease(array, i, VALUE_1); - long x = (long) vh.getAcquire(array, i); - assertEquals(x, VALUE_1, "setRelease long value"); - } - - // Opaque - { - vh.setOpaque(array, i, VALUE_2); - long x = (long) vh.getOpaque(array, i); - assertEquals(x, VALUE_2, "setOpaque long value"); - } - - vh.set(array, i, VALUE_1); - - // Compare - { - boolean r = vh.compareAndSet(array, i, VALUE_1, VALUE_2); - assertEquals(r, true, "success compareAndSet long"); - long x = (long) vh.get(array, i); - assertEquals(x, VALUE_2, "success compareAndSet long value"); - } - - { - boolean r = vh.compareAndSet(array, i, VALUE_1, VALUE_3); - assertEquals(r, false, "failing compareAndSet long"); - long x = (long) vh.get(array, i); - assertEquals(x, VALUE_2, "failing compareAndSet long value"); - } - - { - long r = (long) vh.compareAndExchange(array, i, VALUE_2, VALUE_1); - assertEquals(r, VALUE_2, "success compareAndExchange long"); - long x = (long) vh.get(array, i); - assertEquals(x, VALUE_1, "success compareAndExchange long value"); - } - - { - long r = (long) vh.compareAndExchange(array, i, VALUE_2, VALUE_3); - assertEquals(r, VALUE_1, "failing compareAndExchange long"); - long x = (long) vh.get(array, i); - assertEquals(x, VALUE_1, "failing compareAndExchange long value"); - } - - { - long r = (long) vh.compareAndExchangeAcquire(array, i, VALUE_1, VALUE_2); - assertEquals(r, VALUE_1, "success compareAndExchangeAcquire long"); - long x = (long) vh.get(array, i); - assertEquals(x, VALUE_2, "success compareAndExchangeAcquire long value"); - } - - { - long r = (long) vh.compareAndExchangeAcquire(array, i, VALUE_1, VALUE_3); - assertEquals(r, VALUE_2, "failing compareAndExchangeAcquire long"); - long x = (long) vh.get(array, i); - assertEquals(x, VALUE_2, "failing compareAndExchangeAcquire long value"); - } - - { - long r = (long) vh.compareAndExchangeRelease(array, i, VALUE_2, VALUE_1); - assertEquals(r, VALUE_2, "success compareAndExchangeRelease long"); - long x = (long) vh.get(array, i); - assertEquals(x, VALUE_1, "success compareAndExchangeRelease long value"); - } - - { - long r = (long) vh.compareAndExchangeRelease(array, i, VALUE_2, VALUE_3); - assertEquals(r, VALUE_1, "failing compareAndExchangeRelease long"); - long x = (long) vh.get(array, i); - assertEquals(x, VALUE_1, "failing compareAndExchangeRelease long value"); - } - - { - boolean success = false; - for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) { - success = vh.weakCompareAndSetPlain(array, i, VALUE_1, VALUE_2); - if (!success) weakDelay(); - } - assertEquals(success, true, "success weakCompareAndSetPlain long"); - long x = (long) vh.get(array, i); - assertEquals(x, VALUE_2, "success weakCompareAndSetPlain long value"); - } - - { - boolean success = vh.weakCompareAndSetPlain(array, i, VALUE_1, VALUE_3); - assertEquals(success, false, "failing weakCompareAndSetPlain long"); - long x = (long) vh.get(array, i); - assertEquals(x, VALUE_2, "failing weakCompareAndSetPlain long value"); - } - - { - boolean success = false; - for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) { - success = vh.weakCompareAndSetAcquire(array, i, VALUE_2, VALUE_1); - if (!success) weakDelay(); - } - assertEquals(success, true, "success weakCompareAndSetAcquire long"); - long x = (long) vh.get(array, i); - assertEquals(x, VALUE_1, "success weakCompareAndSetAcquire long"); - } - - { - boolean success = vh.weakCompareAndSetAcquire(array, i, VALUE_2, VALUE_3); - assertEquals(success, false, "failing weakCompareAndSetAcquire long"); - long x = (long) vh.get(array, i); - assertEquals(x, VALUE_1, "failing weakCompareAndSetAcquire long value"); - } - - { - boolean success = false; - for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) { - success = vh.weakCompareAndSetRelease(array, i, VALUE_1, VALUE_2); - if (!success) weakDelay(); - } - assertEquals(success, true, "success weakCompareAndSetRelease long"); - long x = (long) vh.get(array, i); - assertEquals(x, VALUE_2, "success weakCompareAndSetRelease long"); - } - - { - boolean success = vh.weakCompareAndSetRelease(array, i, VALUE_1, VALUE_3); - assertEquals(success, false, "failing weakCompareAndSetRelease long"); - long x = (long) vh.get(array, i); - assertEquals(x, VALUE_2, "failing weakCompareAndSetRelease long value"); - } - - { - boolean success = false; - for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) { - success = vh.weakCompareAndSet(array, i, VALUE_2, VALUE_1); - if (!success) weakDelay(); - } - assertEquals(success, true, "success weakCompareAndSet long"); - long x = (long) vh.get(array, i); - assertEquals(x, VALUE_1, "success weakCompareAndSet long"); - } - - { - boolean success = vh.weakCompareAndSet(array, i, VALUE_2, VALUE_3); - assertEquals(success, false, "failing weakCompareAndSet long"); - long x = (long) vh.get(array, i); - assertEquals(x, VALUE_1, "failing weakCompareAndSet long value"); - } - - // Compare set and get - { - vh.set(array, i, VALUE_1); - - long o = (long) vh.getAndSet(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndSet long"); - long x = (long) vh.get(array, i); - assertEquals(x, VALUE_2, "getAndSet long value"); - } - - { - vh.set(array, i, VALUE_1); - - long o = (long) vh.getAndSetAcquire(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndSetAcquire long"); - long x = (long) vh.get(array, i); - assertEquals(x, VALUE_2, "getAndSetAcquire long value"); - } - - { - vh.set(array, i, VALUE_1); - - long o = (long) vh.getAndSetRelease(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndSetRelease long"); - long x = (long) vh.get(array, i); - assertEquals(x, VALUE_2, "getAndSetRelease long value"); - } - - // get and add, add and get - { - vh.set(array, i, VALUE_1); - - long o = (long) vh.getAndAdd(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndAdd long"); - long x = (long) vh.get(array, i); - assertEquals(x, VALUE_1 + VALUE_2, "getAndAdd long value"); - } - - { - vh.set(array, i, VALUE_1); - - long o = (long) vh.getAndAddAcquire(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndAddAcquire long"); - long x = (long) vh.get(array, i); - assertEquals(x, VALUE_1 + VALUE_2, "getAndAddAcquire long value"); - } - - { - vh.set(array, i, VALUE_1); - - long o = (long) vh.getAndAddRelease(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndAddRelease long"); - long x = (long) vh.get(array, i); - assertEquals(x, VALUE_1 + VALUE_2, "getAndAddRelease long value"); - } - - // get and bitwise or - { - vh.set(array, i, VALUE_1); - - long o = (long) vh.getAndBitwiseOr(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndBitwiseOr long"); - long x = (long) vh.get(array, i); - assertEquals(x, VALUE_1 | VALUE_2, "getAndBitwiseOr long value"); - } - - { - vh.set(array, i, VALUE_1); - - long o = (long) vh.getAndBitwiseOrAcquire(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndBitwiseOrAcquire long"); - long x = (long) vh.get(array, i); - assertEquals(x, VALUE_1 | VALUE_2, "getAndBitwiseOrAcquire long value"); - } - - { - vh.set(array, i, VALUE_1); - - long o = (long) vh.getAndBitwiseOrRelease(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndBitwiseOrRelease long"); - long x = (long) vh.get(array, i); - assertEquals(x, VALUE_1 | VALUE_2, "getAndBitwiseOrRelease long value"); - } - - // get and bitwise and - { - vh.set(array, i, VALUE_1); - - long o = (long) vh.getAndBitwiseAnd(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndBitwiseAnd long"); - long x = (long) vh.get(array, i); - assertEquals(x, VALUE_1 & VALUE_2, "getAndBitwiseAnd long value"); - } - - { - vh.set(array, i, VALUE_1); - - long o = (long) vh.getAndBitwiseAndAcquire(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndBitwiseAndAcquire long"); - long x = (long) vh.get(array, i); - assertEquals(x, VALUE_1 & VALUE_2, "getAndBitwiseAndAcquire long value"); - } - - { - vh.set(array, i, VALUE_1); - - long o = (long) vh.getAndBitwiseAndRelease(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndBitwiseAndRelease long"); - long x = (long) vh.get(array, i); - assertEquals(x, VALUE_1 & VALUE_2, "getAndBitwiseAndRelease long value"); - } - - // get and bitwise xor - { - vh.set(array, i, VALUE_1); - - long o = (long) vh.getAndBitwiseXor(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndBitwiseXor long"); - long x = (long) vh.get(array, i); - assertEquals(x, VALUE_1 ^ VALUE_2, "getAndBitwiseXor long value"); - } - - { - vh.set(array, i, VALUE_1); - - long o = (long) vh.getAndBitwiseXorAcquire(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndBitwiseXorAcquire long"); - long x = (long) vh.get(array, i); - assertEquals(x, VALUE_1 ^ VALUE_2, "getAndBitwiseXorAcquire long value"); - } - - { - vh.set(array, i, VALUE_1); - - long o = (long) vh.getAndBitwiseXorRelease(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndBitwiseXorRelease long"); - long x = (long) vh.get(array, i); - assertEquals(x, VALUE_1 ^ VALUE_2, "getAndBitwiseXorRelease long value"); - } - } } } @@ -1483,12 +1049,10 @@ public class VarHandleTestByteArrayAsLong extends VarHandleBaseByteArrayTest { VarHandle vh = vhs.s; ByteBuffer array = bs.s; - int misalignmentAtZero = array.alignmentOffset(0, SIZE); - bs.fill((byte) 0xff); int length = array.limit() - SIZE + 1; for (int i = 0; i < length; i++) { - boolean iAligned = ((i + misalignmentAtZero) & (SIZE - 1)) == 0; + boolean iAligned = array.isDirect() ? ((i + array.alignmentOffset(0, SIZE)) & (SIZE - 1)) == 0 : false; // Plain { @@ -1797,15 +1361,13 @@ public class VarHandleTestByteArrayAsLong extends VarHandleBaseByteArrayTest { VarHandle vh = vhs.s; ByteBuffer array = bs.s; - int misalignmentAtZero = array.alignmentOffset(0, SIZE); - ByteBuffer bb = ByteBuffer.allocate(SIZE); bb.order(MemoryMode.BIG_ENDIAN.isSet(vhs.memoryModes) ? ByteOrder.BIG_ENDIAN : ByteOrder.LITTLE_ENDIAN); bs.fill(bb.putLong(0, VALUE_2).array()); int length = array.limit() - SIZE + 1; for (int i = 0; i < length; i++) { - boolean iAligned = ((i + misalignmentAtZero) & (SIZE - 1)) == 0; + boolean iAligned = array.isDirect() ? ((i + array.alignmentOffset(0, SIZE)) & (SIZE - 1)) == 0 : false; long v = MemoryMode.BIG_ENDIAN.isSet(vhs.memoryModes) ? rotateLeft(VALUE_2, (i % SIZE) << 3) diff --git a/test/jdk/java/lang/invoke/VarHandles/VarHandleTestByteArrayAsShort.java b/test/jdk/java/lang/invoke/VarHandles/VarHandleTestByteArrayAsShort.java index d25d24cdeab..20751c9d764 100644 --- a/test/jdk/java/lang/invoke/VarHandles/VarHandleTestByteArrayAsShort.java +++ b/test/jdk/java/lang/invoke/VarHandles/VarHandleTestByteArrayAsShort.java @@ -72,12 +72,12 @@ public class VarHandleTestByteArrayAsShort extends VarHandleBaseByteArrayTest { arrayType = int[].class; } VarHandleSource aeh = new VarHandleSource( - MethodHandles.byteArrayViewVarHandle(arrayType, bo), + MethodHandles.byteArrayViewVarHandle(arrayType, bo), false, endianess, MemoryMode.READ_WRITE); vhss.add(aeh); VarHandleSource bbh = new VarHandleSource( - MethodHandles.byteBufferViewVarHandle(arrayType, bo), + MethodHandles.byteBufferViewVarHandle(arrayType, bo), true, endianess, MemoryMode.READ_WRITE); vhss.add(bbh); } @@ -114,38 +114,48 @@ public class VarHandleTestByteArrayAsShort extends VarHandleBaseByteArrayTest { assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET)); assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_VOLATILE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_VOLATILE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_ACQUIRE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_RELEASE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_OPAQUE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_OPAQUE)); + if (vhs.supportsAtomicAccess) { + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_VOLATILE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_VOLATILE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_ACQUIRE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_RELEASE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_OPAQUE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_OPAQUE)); + } else { + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_VOLATILE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.SET_VOLATILE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.SET_RELEASE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_OPAQUE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.SET_OPAQUE)); + } - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_SET)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_ACQUIRE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_RELEASE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_PLAIN)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_ACQUIRE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_RELEASE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET_ACQUIRE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET_RELEASE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_SET)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_RELEASE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_PLAIN)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_RELEASE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET_RELEASE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD_ACQUIRE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD_RELEASE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD_RELEASE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR_ACQUIRE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR_RELEASE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND_ACQUIRE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND_RELEASE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR_ACQUIRE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR_RELEASE)); + + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR_RELEASE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND_RELEASE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR_RELEASE)); } @Test(dataProvider = "typesProvider") @@ -180,9 +190,6 @@ public class VarHandleTestByteArrayAsShort extends VarHandleBaseByteArrayTest { cases.add(new VarHandleSourceAccessTestCase( "index out of bounds", bav, vh, h -> testArrayIndexOutOfBounds(bas, h), false)); - cases.add(new VarHandleSourceAccessTestCase( - "misaligned access", bav, vh, h -> testArrayMisalignedAccess(bas, h), - false)); } else { ByteBufferSource bbs = (ByteBufferSource) bav; @@ -207,9 +214,11 @@ public class VarHandleTestByteArrayAsShort extends VarHandleBaseByteArrayTest { cases.add(new VarHandleSourceAccessTestCase( "index out of bounds", bav, vh, h -> testArrayIndexOutOfBounds(bbs, h), false)); - cases.add(new VarHandleSourceAccessTestCase( - "misaligned access", bav, vh, h -> testArrayMisalignedAccess(bbs, h), - false)); + if (bbs.s.isDirect()) { + cases.add(new VarHandleSourceAccessTestCase( + "misaligned access", bav, vh, h -> testArrayMisalignedAccess(bbs, h), + false)); + } } } } @@ -243,33 +252,6 @@ public class VarHandleTestByteArrayAsShort extends VarHandleBaseByteArrayTest { checkNPE(() -> { vh.set(array, ci, VALUE_1); }); - - checkNPE(() -> { - short x = (short) vh.getVolatile(array, ci); - }); - - checkNPE(() -> { - short x = (short) vh.getAcquire(array, ci); - }); - - checkNPE(() -> { - short x = (short) vh.getOpaque(array, ci); - }); - - checkNPE(() -> { - vh.setVolatile(array, ci, VALUE_1); - }); - - checkNPE(() -> { - vh.setRelease(array, ci, VALUE_1); - }); - - checkNPE(() -> { - vh.setOpaque(array, ci, VALUE_1); - }); - - - } static void testArrayNPE(ByteBufferSource bs, VarHandleSource vhs) { @@ -423,7 +405,7 @@ public class VarHandleTestByteArrayAsShort extends VarHandleBaseByteArrayTest { }); } - if (readOnly) { + if (readOnly && array.isDirect()) { checkROBE(() -> { vh.setVolatile(array, ci, VALUE_1); }); @@ -435,6 +417,11 @@ public class VarHandleTestByteArrayAsShort extends VarHandleBaseByteArrayTest { checkROBE(() -> { vh.setOpaque(array, ci, VALUE_1); }); + + + } + + if (array.isDirect()) { checkUOE(() -> { boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); }); @@ -478,7 +465,6 @@ public class VarHandleTestByteArrayAsShort extends VarHandleBaseByteArrayTest { checkUOE(() -> { short o = (short) vh.getAndSetRelease(array, ci, VALUE_1); }); - checkUOE(() -> { short o = (short) vh.getAndAdd(array, ci, VALUE_1); }); @@ -490,7 +476,6 @@ public class VarHandleTestByteArrayAsShort extends VarHandleBaseByteArrayTest { checkUOE(() -> { short o = (short) vh.getAndAddRelease(array, ci, VALUE_1); }); - checkUOE(() -> { short o = (short) vh.getAndBitwiseOr(array, ci, VALUE_1); }); @@ -526,8 +511,18 @@ public class VarHandleTestByteArrayAsShort extends VarHandleBaseByteArrayTest { checkUOE(() -> { short o = (short) vh.getAndBitwiseXorRelease(array, ci, VALUE_1); }); - } - else { + } else { + checkISE(() -> { + vh.setVolatile(array, ci, VALUE_1); + }); + + checkISE(() -> { + vh.setRelease(array, ci, VALUE_1); + }); + + checkISE(() -> { + vh.setOpaque(array, ci, VALUE_1); + }); checkUOE(() -> { boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); }); @@ -636,33 +631,6 @@ public class VarHandleTestByteArrayAsShort extends VarHandleBaseByteArrayTest { checkAIOOBE(() -> { vh.set(array, ci, VALUE_1); }); - - checkAIOOBE(() -> { - short x = (short) vh.getVolatile(array, ci); - }); - - checkAIOOBE(() -> { - short x = (short) vh.getAcquire(array, ci); - }); - - checkAIOOBE(() -> { - short x = (short) vh.getOpaque(array, ci); - }); - - checkAIOOBE(() -> { - vh.setVolatile(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - vh.setRelease(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - vh.setOpaque(array, ci, VALUE_1); - }); - - - } } @@ -686,74 +654,35 @@ public class VarHandleTestByteArrayAsShort extends VarHandleBaseByteArrayTest { }); } - checkIOOBE(() -> { - short x = (short) vh.getVolatile(array, ci); - }); - - checkIOOBE(() -> { - short x = (short) vh.getAcquire(array, ci); - }); - - checkIOOBE(() -> { - short x = (short) vh.getOpaque(array, ci); - }); - - if (!readOnly) { + if (array.isDirect()) { checkIOOBE(() -> { - vh.setVolatile(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - vh.setRelease(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - vh.setOpaque(array, ci, VALUE_1); - }); - - - - } - } - } - - static void testArrayMisalignedAccess(ByteArraySource bs, VarHandleSource vhs) throws Throwable { - VarHandle vh = vhs.s; - byte[] array = bs.s; - - int misalignmentAtZero = ByteBuffer.wrap(array).alignmentOffset(0, SIZE); - - int length = array.length - SIZE + 1; - for (int i = 0; i < length; i++) { - boolean iAligned = ((i + misalignmentAtZero) & (SIZE - 1)) == 0; - final int ci = i; - - if (!iAligned) { - checkISE(() -> { short x = (short) vh.getVolatile(array, ci); }); - checkISE(() -> { + checkIOOBE(() -> { short x = (short) vh.getAcquire(array, ci); }); - checkISE(() -> { + checkIOOBE(() -> { short x = (short) vh.getOpaque(array, ci); }); - checkISE(() -> { - vh.setVolatile(array, ci, VALUE_1); - }); + if (!readOnly) { + checkIOOBE(() -> { + vh.setVolatile(array, ci, VALUE_1); + }); - checkISE(() -> { - vh.setRelease(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + vh.setRelease(array, ci, VALUE_1); + }); - checkISE(() -> { - vh.setOpaque(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + vh.setOpaque(array, ci, VALUE_1); + }); + + } } } } @@ -795,9 +724,6 @@ public class VarHandleTestByteArrayAsShort extends VarHandleBaseByteArrayTest { checkISE(() -> { vh.setOpaque(array, ci, VALUE_1); }); - - - } } } @@ -807,45 +733,15 @@ public class VarHandleTestByteArrayAsShort extends VarHandleBaseByteArrayTest { VarHandle vh = vhs.s; byte[] array = bs.s; - int misalignmentAtZero = ByteBuffer.wrap(array).alignmentOffset(0, SIZE); - bs.fill((byte) 0xff); int length = array.length - SIZE + 1; for (int i = 0; i < length; i++) { - boolean iAligned = ((i + misalignmentAtZero) & (SIZE - 1)) == 0; - // Plain { vh.set(array, i, VALUE_1); short x = (short) vh.get(array, i); assertEquals(x, VALUE_1, "get short value"); } - - - if (iAligned) { - // Volatile - { - vh.setVolatile(array, i, VALUE_2); - short x = (short) vh.getVolatile(array, i); - assertEquals(x, VALUE_2, "setVolatile short value"); - } - - // Lazy - { - vh.setRelease(array, i, VALUE_1); - short x = (short) vh.getAcquire(array, i); - assertEquals(x, VALUE_1, "setRelease short value"); - } - - // Opaque - { - vh.setOpaque(array, i, VALUE_2); - short x = (short) vh.getOpaque(array, i); - assertEquals(x, VALUE_2, "setOpaque short value"); - } - - - } } } @@ -854,12 +750,10 @@ public class VarHandleTestByteArrayAsShort extends VarHandleBaseByteArrayTest { VarHandle vh = vhs.s; ByteBuffer array = bs.s; - int misalignmentAtZero = array.alignmentOffset(0, SIZE); - bs.fill((byte) 0xff); int length = array.limit() - SIZE + 1; for (int i = 0; i < length; i++) { - boolean iAligned = ((i + misalignmentAtZero) & (SIZE - 1)) == 0; + boolean iAligned = array.isDirect() ? ((i + array.alignmentOffset(0, SIZE)) & (SIZE - 1)) == 0 : false; // Plain { @@ -899,15 +793,13 @@ public class VarHandleTestByteArrayAsShort extends VarHandleBaseByteArrayTest { VarHandle vh = vhs.s; ByteBuffer array = bs.s; - int misalignmentAtZero = array.alignmentOffset(0, SIZE); - ByteBuffer bb = ByteBuffer.allocate(SIZE); bb.order(MemoryMode.BIG_ENDIAN.isSet(vhs.memoryModes) ? ByteOrder.BIG_ENDIAN : ByteOrder.LITTLE_ENDIAN); bs.fill(bb.putShort(0, VALUE_2).array()); int length = array.limit() - SIZE + 1; for (int i = 0; i < length; i++) { - boolean iAligned = ((i + misalignmentAtZero) & (SIZE - 1)) == 0; + boolean iAligned = array.isDirect() ? ((i + array.alignmentOffset(0, SIZE)) & (SIZE - 1)) == 0 : false; short v = MemoryMode.BIG_ENDIAN.isSet(vhs.memoryModes) ? rotateLeft(VALUE_2, (i % SIZE) << 3) diff --git a/test/jdk/java/lang/invoke/VarHandles/X-VarHandleTestByteArrayView.java.template b/test/jdk/java/lang/invoke/VarHandles/X-VarHandleTestByteArrayView.java.template index 84111ac5eb7..a79dbb3547e 100644 --- a/test/jdk/java/lang/invoke/VarHandles/X-VarHandleTestByteArrayView.java.template +++ b/test/jdk/java/lang/invoke/VarHandles/X-VarHandleTestByteArrayView.java.template @@ -76,12 +76,12 @@ public class VarHandleTestByteArrayAs$Type$ extends VarHandleBaseByteArrayTest { #end[int] } VarHandleSource aeh = new VarHandleSource( - MethodHandles.byteArrayViewVarHandle(arrayType, bo), + MethodHandles.byteArrayViewVarHandle(arrayType, bo), false, endianess, MemoryMode.READ_WRITE); vhss.add(aeh); VarHandleSource bbh = new VarHandleSource( - MethodHandles.byteBufferViewVarHandle(arrayType, bo), + MethodHandles.byteBufferViewVarHandle(arrayType, bo), true, endianess, MemoryMode.READ_WRITE); vhss.add(bbh); } @@ -118,69 +118,91 @@ public class VarHandleTestByteArrayAs$Type$ extends VarHandleBaseByteArrayTest { assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET)); assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_VOLATILE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_VOLATILE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_ACQUIRE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_RELEASE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_OPAQUE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_OPAQUE)); + if (vhs.supportsAtomicAccess) { + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_VOLATILE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_VOLATILE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_ACQUIRE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_RELEASE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_OPAQUE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.SET_OPAQUE)); + } else { + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_VOLATILE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.SET_VOLATILE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.SET_RELEASE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_OPAQUE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.SET_OPAQUE)); + } #if[CAS] - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_SET)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_ACQUIRE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_RELEASE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_PLAIN)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_ACQUIRE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_RELEASE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET_ACQUIRE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET_RELEASE)); -#else[CAS] - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_SET)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_ACQUIRE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_RELEASE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_PLAIN)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_ACQUIRE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_RELEASE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET_ACQUIRE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET_RELEASE)); + if (vhs.supportsAtomicAccess) { + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_SET)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_ACQUIRE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_RELEASE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_PLAIN)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_ACQUIRE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_RELEASE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET_ACQUIRE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET_RELEASE)); + } else { +#end[CAS] + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_SET)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.COMPARE_AND_EXCHANGE_RELEASE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_PLAIN)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.WEAK_COMPARE_AND_SET_RELEASE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_SET_RELEASE)); +#if[CAS] + } #end[CAS] #if[AtomicAdd] - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD_ACQUIRE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD_RELEASE)); -#else[AtomicAdd] - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD_ACQUIRE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD_RELEASE)); + if (vhs.supportsAtomicAccess) { + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD_ACQUIRE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD_RELEASE)); + } else { +#end[AtomicAdd] + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_ADD_RELEASE)); +#if[AtomicAdd] + } #end[AtomicAdd] + #if[Bitwise] - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR_ACQUIRE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR_RELEASE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND_ACQUIRE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND_RELEASE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR_ACQUIRE)); - assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR_RELEASE)); -#else[Bitwise] - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR_ACQUIRE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR_RELEASE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND_ACQUIRE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND_RELEASE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR_ACQUIRE)); - assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR_RELEASE)); + if (vhs.supportsAtomicAccess) { + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR_ACQUIRE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR_RELEASE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND_ACQUIRE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND_RELEASE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR_ACQUIRE)); + assertTrue(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR_RELEASE)); + } else { +#end[Bitwise] + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_OR_RELEASE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_AND_RELEASE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR_ACQUIRE)); + assertFalse(vh.isAccessModeSupported(VarHandle.AccessMode.GET_AND_BITWISE_XOR_RELEASE)); +#if[Bitwise] + } #end[Bitwise] } @@ -216,9 +238,6 @@ public class VarHandleTestByteArrayAs$Type$ extends VarHandleBaseByteArrayTest { cases.add(new VarHandleSourceAccessTestCase( "index out of bounds", bav, vh, h -> testArrayIndexOutOfBounds(bas, h), false)); - cases.add(new VarHandleSourceAccessTestCase( - "misaligned access", bav, vh, h -> testArrayMisalignedAccess(bas, h), - false)); } else { ByteBufferSource bbs = (ByteBufferSource) bav; @@ -243,9 +262,11 @@ public class VarHandleTestByteArrayAs$Type$ extends VarHandleBaseByteArrayTest { cases.add(new VarHandleSourceAccessTestCase( "index out of bounds", bav, vh, h -> testArrayIndexOutOfBounds(bbs, h), false)); - cases.add(new VarHandleSourceAccessTestCase( - "misaligned access", bav, vh, h -> testArrayMisalignedAccess(bbs, h), - false)); + if (bbs.s.isDirect()) { + cases.add(new VarHandleSourceAccessTestCase( + "misaligned access", bav, vh, h -> testArrayMisalignedAccess(bbs, h), + false)); + } } } } @@ -279,128 +300,6 @@ public class VarHandleTestByteArrayAs$Type$ extends VarHandleBaseByteArrayTest { checkNPE(() -> { vh.set(array, ci, VALUE_1); }); - - checkNPE(() -> { - $type$ x = ($type$) vh.getVolatile(array, ci); - }); - - checkNPE(() -> { - $type$ x = ($type$) vh.getAcquire(array, ci); - }); - - checkNPE(() -> { - $type$ x = ($type$) vh.getOpaque(array, ci); - }); - - checkNPE(() -> { - vh.setVolatile(array, ci, VALUE_1); - }); - - checkNPE(() -> { - vh.setRelease(array, ci, VALUE_1); - }); - - checkNPE(() -> { - vh.setOpaque(array, ci, VALUE_1); - }); - -#if[CAS] - checkNPE(() -> { - boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); - }); - - checkNPE(() -> { - $type$ r = ($type$) vh.compareAndExchange(array, ci, VALUE_2, VALUE_1); - }); - - checkNPE(() -> { - $type$ r = ($type$) vh.compareAndExchangeAcquire(array, ci, VALUE_2, VALUE_1); - }); - - checkNPE(() -> { - $type$ r = ($type$) vh.compareAndExchangeRelease(array, ci, VALUE_2, VALUE_1); - }); - - checkNPE(() -> { - boolean r = vh.weakCompareAndSetPlain(array, ci, VALUE_1, VALUE_2); - }); - - checkNPE(() -> { - boolean r = vh.weakCompareAndSet(array, ci, VALUE_1, VALUE_2); - }); - - checkNPE(() -> { - boolean r = vh.weakCompareAndSetAcquire(array, ci, VALUE_1, VALUE_2); - }); - - checkNPE(() -> { - boolean r = vh.weakCompareAndSetRelease(array, ci, VALUE_1, VALUE_2); - }); - - checkNPE(() -> { - $type$ o = ($type$) vh.getAndSet(array, ci, VALUE_1); - }); - - checkNPE(() -> { - $type$ o = ($type$) vh.getAndSetAcquire(array, ci, VALUE_1); - }); - - checkNPE(() -> { - $type$ o = ($type$) vh.getAndSetRelease(array, ci, VALUE_1); - }); -#end[CAS] - -#if[AtomicAdd] - checkNPE(() -> { - $type$ o = ($type$) vh.getAndAdd(array, ci, VALUE_1); - }); - - checkNPE(() -> { - $type$ o = ($type$) vh.getAndAddAcquire(array, ci, VALUE_1); - }); - - checkNPE(() -> { - $type$ o = ($type$) vh.getAndAddRelease(array, ci, VALUE_1); - }); -#end[AtomicAdd] - -#if[Bitwise] - checkNPE(() -> { - $type$ o = ($type$) vh.getAndBitwiseOr(array, ci, VALUE_1); - }); - - checkNPE(() -> { - $type$ o = ($type$) vh.getAndBitwiseOrAcquire(array, ci, VALUE_1); - }); - - checkNPE(() -> { - $type$ o = ($type$) vh.getAndBitwiseOrRelease(array, ci, VALUE_1); - }); - - checkNPE(() -> { - $type$ o = ($type$) vh.getAndBitwiseAnd(array, ci, VALUE_1); - }); - - checkNPE(() -> { - $type$ o = ($type$) vh.getAndBitwiseAndAcquire(array, ci, VALUE_1); - }); - - checkNPE(() -> { - $type$ o = ($type$) vh.getAndBitwiseAndRelease(array, ci, VALUE_1); - }); - - checkNPE(() -> { - $type$ o = ($type$) vh.getAndBitwiseXor(array, ci, VALUE_1); - }); - - checkNPE(() -> { - $type$ o = ($type$) vh.getAndBitwiseXorAcquire(array, ci, VALUE_1); - }); - - checkNPE(() -> { - $type$ o = ($type$) vh.getAndBitwiseXorRelease(array, ci, VALUE_1); - }); -#end[Bitwise] } static void testArrayNPE(ByteBufferSource bs, VarHandleSource vhs) { @@ -544,7 +443,6 @@ public class VarHandleTestByteArrayAs$Type$ extends VarHandleBaseByteArrayTest { byte[] array = bs.s; int ci = 1; -#if[!CAS] checkUOE(() -> { boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); }); @@ -588,9 +486,7 @@ public class VarHandleTestByteArrayAs$Type$ extends VarHandleBaseByteArrayTest { checkUOE(() -> { $type$ o = ($type$) vh.getAndSetRelease(array, ci, VALUE_1); }); -#end[CAS] -#if[!AtomicAdd] checkUOE(() -> { $type$ o = ($type$) vh.getAndAdd(array, ci, VALUE_1); }); @@ -602,9 +498,7 @@ public class VarHandleTestByteArrayAs$Type$ extends VarHandleBaseByteArrayTest { checkUOE(() -> { $type$ o = ($type$) vh.getAndAddRelease(array, ci, VALUE_1); }); -#end[AtomicAdd] -#if[!Bitwise] checkUOE(() -> { $type$ o = ($type$) vh.getAndBitwiseOr(array, ci, VALUE_1); }); @@ -640,7 +534,6 @@ public class VarHandleTestByteArrayAs$Type$ extends VarHandleBaseByteArrayTest { checkUOE(() -> { $type$ o = ($type$) vh.getAndBitwiseXorRelease(array, ci, VALUE_1); }); -#end[Bitwise] } static void testArrayUnsupported(ByteBufferSource bs, VarHandleSource vhs) { @@ -655,7 +548,7 @@ public class VarHandleTestByteArrayAs$Type$ extends VarHandleBaseByteArrayTest { }); } - if (readOnly) { + if (readOnly && array.isDirect()) { checkROBE(() -> { vh.setVolatile(array, ci, VALUE_1); }); @@ -668,7 +561,6 @@ public class VarHandleTestByteArrayAs$Type$ extends VarHandleBaseByteArrayTest { vh.setOpaque(array, ci, VALUE_1); }); #if[CAS] - checkROBE(() -> { boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); }); @@ -712,51 +604,6 @@ public class VarHandleTestByteArrayAs$Type$ extends VarHandleBaseByteArrayTest { checkROBE(() -> { $type$ o = ($type$) vh.getAndSetRelease(array, ci, VALUE_1); }); - -#else[CAS] - checkUOE(() -> { - boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); - }); - - checkUOE(() -> { - $type$ r = ($type$) vh.compareAndExchange(array, ci, VALUE_2, VALUE_1); - }); - - checkUOE(() -> { - $type$ r = ($type$) vh.compareAndExchangeAcquire(array, ci, VALUE_2, VALUE_1); - }); - - checkUOE(() -> { - $type$ r = ($type$) vh.compareAndExchangeRelease(array, ci, VALUE_2, VALUE_1); - }); - - checkUOE(() -> { - boolean r = vh.weakCompareAndSetPlain(array, ci, VALUE_1, VALUE_2); - }); - - checkUOE(() -> { - boolean r = vh.weakCompareAndSet(array, ci, VALUE_1, VALUE_2); - }); - - checkUOE(() -> { - boolean r = vh.weakCompareAndSetAcquire(array, ci, VALUE_1, VALUE_2); - }); - - checkUOE(() -> { - boolean r = vh.weakCompareAndSetRelease(array, ci, VALUE_1, VALUE_2); - }); - - checkUOE(() -> { - $type$ o = ($type$) vh.getAndSet(array, ci, VALUE_1); - }); - - checkUOE(() -> { - $type$ o = ($type$) vh.getAndSetAcquire(array, ci, VALUE_1); - }); - - checkUOE(() -> { - $type$ o = ($type$) vh.getAndSetRelease(array, ci, VALUE_1); - }); #end[CAS] #if[AtomicAdd] @@ -771,18 +618,6 @@ public class VarHandleTestByteArrayAs$Type$ extends VarHandleBaseByteArrayTest { checkROBE(() -> { $type$ o = ($type$) vh.getAndAddRelease(array, ci, VALUE_1); }); -#else[AtomicAdd] - checkUOE(() -> { - $type$ o = ($type$) vh.getAndAdd(array, ci, VALUE_1); - }); - - checkUOE(() -> { - $type$ o = ($type$) vh.getAndAddAcquire(array, ci, VALUE_1); - }); - - checkUOE(() -> { - $type$ o = ($type$) vh.getAndAddRelease(array, ci, VALUE_1); - }); #end[AtomicAdd] #if[Bitwise] @@ -821,45 +656,10 @@ public class VarHandleTestByteArrayAs$Type$ extends VarHandleBaseByteArrayTest { checkROBE(() -> { $type$ o = ($type$) vh.getAndBitwiseXorRelease(array, ci, VALUE_1); }); -#else[Bitwise] - checkUOE(() -> { - $type$ o = ($type$) vh.getAndBitwiseOr(array, ci, VALUE_1); - }); - - checkUOE(() -> { - $type$ o = ($type$) vh.getAndBitwiseOrAcquire(array, ci, VALUE_1); - }); - - checkUOE(() -> { - $type$ o = ($type$) vh.getAndBitwiseOrRelease(array, ci, VALUE_1); - }); - - checkUOE(() -> { - $type$ o = ($type$) vh.getAndBitwiseAnd(array, ci, VALUE_1); - }); - - checkUOE(() -> { - $type$ o = ($type$) vh.getAndBitwiseAndAcquire(array, ci, VALUE_1); - }); - - checkUOE(() -> { - $type$ o = ($type$) vh.getAndBitwiseAndRelease(array, ci, VALUE_1); - }); - - checkUOE(() -> { - $type$ o = ($type$) vh.getAndBitwiseXor(array, ci, VALUE_1); - }); - - checkUOE(() -> { - $type$ o = ($type$) vh.getAndBitwiseXorAcquire(array, ci, VALUE_1); - }); - - checkUOE(() -> { - $type$ o = ($type$) vh.getAndBitwiseXorRelease(array, ci, VALUE_1); - }); #end[Bitwise] } - else { + + if (array.isDirect()) { #if[!CAS] checkUOE(() -> { boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); @@ -954,6 +754,205 @@ public class VarHandleTestByteArrayAs$Type$ extends VarHandleBaseByteArrayTest { checkUOE(() -> { $type$ o = ($type$) vh.getAndBitwiseXorRelease(array, ci, VALUE_1); }); +#end[Bitwise] + } else { + checkISE(() -> { + vh.setVolatile(array, ci, VALUE_1); + }); + + checkISE(() -> { + vh.setRelease(array, ci, VALUE_1); + }); + + checkISE(() -> { + vh.setOpaque(array, ci, VALUE_1); + }); +#if[!CAS] + checkUOE(() -> { + boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); + }); + + checkUOE(() -> { + $type$ r = ($type$) vh.compareAndExchange(array, ci, VALUE_2, VALUE_1); + }); + + checkUOE(() -> { + $type$ r = ($type$) vh.compareAndExchangeAcquire(array, ci, VALUE_2, VALUE_1); + }); + + checkUOE(() -> { + $type$ r = ($type$) vh.compareAndExchangeRelease(array, ci, VALUE_2, VALUE_1); + }); + + checkUOE(() -> { + boolean r = vh.weakCompareAndSetPlain(array, ci, VALUE_1, VALUE_2); + }); + + checkUOE(() -> { + boolean r = vh.weakCompareAndSet(array, ci, VALUE_1, VALUE_2); + }); + + checkUOE(() -> { + boolean r = vh.weakCompareAndSetAcquire(array, ci, VALUE_1, VALUE_2); + }); + + checkUOE(() -> { + boolean r = vh.weakCompareAndSetRelease(array, ci, VALUE_1, VALUE_2); + }); + + checkUOE(() -> { + $type$ o = ($type$) vh.getAndSet(array, ci, VALUE_1); + }); + + checkUOE(() -> { + $type$ o = ($type$) vh.getAndSetAcquire(array, ci, VALUE_1); + }); + + checkUOE(() -> { + $type$ o = ($type$) vh.getAndSetRelease(array, ci, VALUE_1); + }); +#else[CAS] + checkISE(() -> { + boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); + }); + + checkISE(() -> { + $type$ r = ($type$) vh.compareAndExchange(array, ci, VALUE_2, VALUE_1); + }); + + checkISE(() -> { + $type$ r = ($type$) vh.compareAndExchangeAcquire(array, ci, VALUE_2, VALUE_1); + }); + + checkISE(() -> { + $type$ r = ($type$) vh.compareAndExchangeRelease(array, ci, VALUE_2, VALUE_1); + }); + + checkISE(() -> { + boolean r = vh.weakCompareAndSetPlain(array, ci, VALUE_1, VALUE_2); + }); + + checkISE(() -> { + boolean r = vh.weakCompareAndSet(array, ci, VALUE_1, VALUE_2); + }); + + checkISE(() -> { + boolean r = vh.weakCompareAndSetAcquire(array, ci, VALUE_1, VALUE_2); + }); + + checkISE(() -> { + boolean r = vh.weakCompareAndSetRelease(array, ci, VALUE_1, VALUE_2); + }); + + checkISE(() -> { + $type$ o = ($type$) vh.getAndSet(array, ci, VALUE_1); + }); + + checkISE(() -> { + $type$ o = ($type$) vh.getAndSetAcquire(array, ci, VALUE_1); + }); + + checkISE(() -> { + $type$ o = ($type$) vh.getAndSetRelease(array, ci, VALUE_1); + }); +#end[CAS] +#if[!AtomicAdd] + checkUOE(() -> { + $type$ o = ($type$) vh.getAndAdd(array, ci, VALUE_1); + }); + + checkUOE(() -> { + $type$ o = ($type$) vh.getAndAddAcquire(array, ci, VALUE_1); + }); + + checkUOE(() -> { + $type$ o = ($type$) vh.getAndAddRelease(array, ci, VALUE_1); + }); +#else[AtomicAdd] + checkISE(() -> { + $type$ o = ($type$) vh.getAndAdd(array, ci, VALUE_1); + }); + + checkISE(() -> { + $type$ o = ($type$) vh.getAndAddAcquire(array, ci, VALUE_1); + }); + + checkISE(() -> { + $type$ o = ($type$) vh.getAndAddRelease(array, ci, VALUE_1); + }); +#end[AtomicAdd] +#if[!Bitwise] + checkUOE(() -> { + $type$ o = ($type$) vh.getAndBitwiseOr(array, ci, VALUE_1); + }); + + checkUOE(() -> { + $type$ o = ($type$) vh.getAndBitwiseOrAcquire(array, ci, VALUE_1); + }); + + checkUOE(() -> { + $type$ o = ($type$) vh.getAndBitwiseOrRelease(array, ci, VALUE_1); + }); + + checkUOE(() -> { + $type$ o = ($type$) vh.getAndBitwiseAnd(array, ci, VALUE_1); + }); + + checkUOE(() -> { + $type$ o = ($type$) vh.getAndBitwiseAndAcquire(array, ci, VALUE_1); + }); + + checkUOE(() -> { + $type$ o = ($type$) vh.getAndBitwiseAndRelease(array, ci, VALUE_1); + }); + + checkUOE(() -> { + $type$ o = ($type$) vh.getAndBitwiseXor(array, ci, VALUE_1); + }); + + checkUOE(() -> { + $type$ o = ($type$) vh.getAndBitwiseXorAcquire(array, ci, VALUE_1); + }); + + checkUOE(() -> { + $type$ o = ($type$) vh.getAndBitwiseXorRelease(array, ci, VALUE_1); + }); +#else[Bitwise] + checkISE(() -> { + $type$ o = ($type$) vh.getAndBitwiseOr(array, ci, VALUE_1); + }); + + checkISE(() -> { + $type$ o = ($type$) vh.getAndBitwiseOrAcquire(array, ci, VALUE_1); + }); + + checkISE(() -> { + $type$ o = ($type$) vh.getAndBitwiseOrRelease(array, ci, VALUE_1); + }); + + checkISE(() -> { + $type$ o = ($type$) vh.getAndBitwiseAnd(array, ci, VALUE_1); + }); + + checkISE(() -> { + $type$ o = ($type$) vh.getAndBitwiseAndAcquire(array, ci, VALUE_1); + }); + + checkISE(() -> { + $type$ o = ($type$) vh.getAndBitwiseAndRelease(array, ci, VALUE_1); + }); + + checkISE(() -> { + $type$ o = ($type$) vh.getAndBitwiseXor(array, ci, VALUE_1); + }); + + checkISE(() -> { + $type$ o = ($type$) vh.getAndBitwiseXorAcquire(array, ci, VALUE_1); + }); + + checkISE(() -> { + $type$ o = ($type$) vh.getAndBitwiseXorRelease(array, ci, VALUE_1); + }); #end[Bitwise] } } @@ -974,129 +973,6 @@ public class VarHandleTestByteArrayAs$Type$ extends VarHandleBaseByteArrayTest { checkAIOOBE(() -> { vh.set(array, ci, VALUE_1); }); - - checkAIOOBE(() -> { - $type$ x = ($type$) vh.getVolatile(array, ci); - }); - - checkAIOOBE(() -> { - $type$ x = ($type$) vh.getAcquire(array, ci); - }); - - checkAIOOBE(() -> { - $type$ x = ($type$) vh.getOpaque(array, ci); - }); - - checkAIOOBE(() -> { - vh.setVolatile(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - vh.setRelease(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - vh.setOpaque(array, ci, VALUE_1); - }); -#if[CAS] - - checkAIOOBE(() -> { - boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); - }); - - checkAIOOBE(() -> { - $type$ r = ($type$) vh.compareAndExchange(array, ci, VALUE_2, VALUE_1); - }); - - checkAIOOBE(() -> { - $type$ r = ($type$) vh.compareAndExchangeAcquire(array, ci, VALUE_2, VALUE_1); - }); - - checkAIOOBE(() -> { - $type$ r = ($type$) vh.compareAndExchangeRelease(array, ci, VALUE_2, VALUE_1); - }); - - checkAIOOBE(() -> { - boolean r = vh.weakCompareAndSetPlain(array, ci, VALUE_1, VALUE_2); - }); - - checkAIOOBE(() -> { - boolean r = vh.weakCompareAndSet(array, ci, VALUE_1, VALUE_2); - }); - - checkAIOOBE(() -> { - boolean r = vh.weakCompareAndSetAcquire(array, ci, VALUE_1, VALUE_2); - }); - - checkAIOOBE(() -> { - boolean r = vh.weakCompareAndSetRelease(array, ci, VALUE_1, VALUE_2); - }); - - checkAIOOBE(() -> { - $type$ o = ($type$) vh.getAndSet(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - $type$ o = ($type$) vh.getAndSetAcquire(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - $type$ o = ($type$) vh.getAndSetRelease(array, ci, VALUE_1); - }); -#end[CAS] - -#if[AtomicAdd] - checkAIOOBE(() -> { - $type$ o = ($type$) vh.getAndAdd(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - $type$ o = ($type$) vh.getAndAddAcquire(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - $type$ o = ($type$) vh.getAndAddRelease(array, ci, VALUE_1); - }); -#end[AtomicAdd] - -#if[Bitwise] - checkAIOOBE(() -> { - $type$ o = ($type$) vh.getAndBitwiseOr(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - $type$ o = ($type$) vh.getAndBitwiseOrAcquire(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - $type$ o = ($type$) vh.getAndBitwiseOrRelease(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - $type$ o = ($type$) vh.getAndBitwiseAnd(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - $type$ o = ($type$) vh.getAndBitwiseAndAcquire(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - $type$ o = ($type$) vh.getAndBitwiseAndRelease(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - $type$ o = ($type$) vh.getAndBitwiseXor(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - $type$ o = ($type$) vh.getAndBitwiseXorAcquire(array, ci, VALUE_1); - }); - - checkAIOOBE(() -> { - $type$ o = ($type$) vh.getAndBitwiseXorRelease(array, ci, VALUE_1); - }); -#end[Bitwise] - } } @@ -1120,265 +996,130 @@ public class VarHandleTestByteArrayAs$Type$ extends VarHandleBaseByteArrayTest { }); } - checkIOOBE(() -> { - $type$ x = ($type$) vh.getVolatile(array, ci); - }); - - checkIOOBE(() -> { - $type$ x = ($type$) vh.getAcquire(array, ci); - }); - - checkIOOBE(() -> { - $type$ x = ($type$) vh.getOpaque(array, ci); - }); - - if (!readOnly) { + if (array.isDirect()) { checkIOOBE(() -> { - vh.setVolatile(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - vh.setRelease(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - vh.setOpaque(array, ci, VALUE_1); - }); - -#if[CAS] - checkIOOBE(() -> { - boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); - }); - - checkIOOBE(() -> { - $type$ r = ($type$) vh.compareAndExchange(array, ci, VALUE_2, VALUE_1); - }); - - checkIOOBE(() -> { - $type$ r = ($type$) vh.compareAndExchangeAcquire(array, ci, VALUE_2, VALUE_1); - }); - - checkIOOBE(() -> { - $type$ r = ($type$) vh.compareAndExchangeRelease(array, ci, VALUE_2, VALUE_1); - }); - - checkIOOBE(() -> { - boolean r = vh.weakCompareAndSetPlain(array, ci, VALUE_1, VALUE_2); - }); - - checkIOOBE(() -> { - boolean r = vh.weakCompareAndSet(array, ci, VALUE_1, VALUE_2); - }); - - checkIOOBE(() -> { - boolean r = vh.weakCompareAndSetAcquire(array, ci, VALUE_1, VALUE_2); - }); - - checkIOOBE(() -> { - boolean r = vh.weakCompareAndSetRelease(array, ci, VALUE_1, VALUE_2); - }); - - checkIOOBE(() -> { - $type$ o = ($type$) vh.getAndSet(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - $type$ o = ($type$) vh.getAndSetAcquire(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - $type$ o = ($type$) vh.getAndSetRelease(array, ci, VALUE_1); - }); -#end[CAS] - -#if[AtomicAdd] - checkIOOBE(() -> { - $type$ o = ($type$) vh.getAndAdd(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - $type$ o = ($type$) vh.getAndAddAcquire(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - $type$ o = ($type$) vh.getAndAddRelease(array, ci, VALUE_1); - }); -#end[AtomicAdd] - -#if[Bitwise] - checkIOOBE(() -> { - $type$ o = ($type$) vh.getAndBitwiseOr(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - $type$ o = ($type$) vh.getAndBitwiseOrAcquire(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - $type$ o = ($type$) vh.getAndBitwiseOrRelease(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - $type$ o = ($type$) vh.getAndBitwiseAnd(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - $type$ o = ($type$) vh.getAndBitwiseAndAcquire(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - $type$ o = ($type$) vh.getAndBitwiseAndRelease(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - $type$ o = ($type$) vh.getAndBitwiseXor(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - $type$ o = ($type$) vh.getAndBitwiseXorAcquire(array, ci, VALUE_1); - }); - - checkIOOBE(() -> { - $type$ o = ($type$) vh.getAndBitwiseXorRelease(array, ci, VALUE_1); - }); -#end[Bitwise] - } - } - } - - static void testArrayMisalignedAccess(ByteArraySource bs, VarHandleSource vhs) throws Throwable { - VarHandle vh = vhs.s; - byte[] array = bs.s; - - int misalignmentAtZero = ByteBuffer.wrap(array).alignmentOffset(0, SIZE); - - int length = array.length - SIZE + 1; - for (int i = 0; i < length; i++) { - boolean iAligned = ((i + misalignmentAtZero) & (SIZE - 1)) == 0; - final int ci = i; - - if (!iAligned) { - checkISE(() -> { $type$ x = ($type$) vh.getVolatile(array, ci); }); - checkISE(() -> { + checkIOOBE(() -> { $type$ x = ($type$) vh.getAcquire(array, ci); }); - checkISE(() -> { + checkIOOBE(() -> { $type$ x = ($type$) vh.getOpaque(array, ci); }); - checkISE(() -> { - vh.setVolatile(array, ci, VALUE_1); - }); + if (!readOnly) { + checkIOOBE(() -> { + vh.setVolatile(array, ci, VALUE_1); + }); - checkISE(() -> { - vh.setRelease(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + vh.setRelease(array, ci, VALUE_1); + }); + + checkIOOBE(() -> { + vh.setOpaque(array, ci, VALUE_1); + }); - checkISE(() -> { - vh.setOpaque(array, ci, VALUE_1); - }); #if[CAS] + checkIOOBE(() -> { + boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); + }); - checkISE(() -> { - boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); - }); + checkIOOBE(() -> { + $type$ r = ($type$) vh.compareAndExchange(array, ci, VALUE_2, VALUE_1); + }); - checkISE(() -> { - $type$ r = ($type$) vh.compareAndExchange(array, ci, VALUE_2, VALUE_1); - }); + checkIOOBE(() -> { + $type$ r = ($type$) vh.compareAndExchangeAcquire(array, ci, VALUE_2, VALUE_1); + }); - checkISE(() -> { - $type$ r = ($type$) vh.compareAndExchangeAcquire(array, ci, VALUE_2, VALUE_1); - }); + checkIOOBE(() -> { + $type$ r = ($type$) vh.compareAndExchangeRelease(array, ci, VALUE_2, VALUE_1); + }); - checkISE(() -> { - $type$ r = ($type$) vh.compareAndExchangeRelease(array, ci, VALUE_2, VALUE_1); - }); + checkIOOBE(() -> { + boolean r = vh.weakCompareAndSetPlain(array, ci, VALUE_1, VALUE_2); + }); - checkISE(() -> { - boolean r = vh.weakCompareAndSetPlain(array, ci, VALUE_1, VALUE_2); - }); + checkIOOBE(() -> { + boolean r = vh.weakCompareAndSet(array, ci, VALUE_1, VALUE_2); + }); - checkISE(() -> { - boolean r = vh.weakCompareAndSet(array, ci, VALUE_1, VALUE_2); - }); + checkIOOBE(() -> { + boolean r = vh.weakCompareAndSetAcquire(array, ci, VALUE_1, VALUE_2); + }); - checkISE(() -> { - boolean r = vh.weakCompareAndSetAcquire(array, ci, VALUE_1, VALUE_2); - }); + checkIOOBE(() -> { + boolean r = vh.weakCompareAndSetRelease(array, ci, VALUE_1, VALUE_2); + }); - checkISE(() -> { - boolean r = vh.weakCompareAndSetRelease(array, ci, VALUE_1, VALUE_2); - }); + checkIOOBE(() -> { + $type$ o = ($type$) vh.getAndSet(array, ci, VALUE_1); + }); - checkISE(() -> { - $type$ o = ($type$) vh.getAndSet(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + $type$ o = ($type$) vh.getAndSetAcquire(array, ci, VALUE_1); + }); - checkISE(() -> { - $type$ o = ($type$) vh.getAndSetAcquire(array, ci, VALUE_1); - }); - - checkISE(() -> { - $type$ o = ($type$) vh.getAndSetRelease(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + $type$ o = ($type$) vh.getAndSetRelease(array, ci, VALUE_1); + }); #end[CAS] #if[AtomicAdd] - checkISE(() -> { - $type$ o = ($type$) vh.getAndAdd(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + $type$ o = ($type$) vh.getAndAdd(array, ci, VALUE_1); + }); - checkISE(() -> { - $type$ o = ($type$) vh.getAndAddAcquire(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + $type$ o = ($type$) vh.getAndAddAcquire(array, ci, VALUE_1); + }); - checkISE(() -> { - $type$ o = ($type$) vh.getAndAddRelease(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + $type$ o = ($type$) vh.getAndAddRelease(array, ci, VALUE_1); + }); #end[AtomicAdd] #if[Bitwise] - checkISE(() -> { - $type$ o = ($type$) vh.getAndBitwiseOr(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + $type$ o = ($type$) vh.getAndBitwiseOr(array, ci, VALUE_1); + }); - checkISE(() -> { - $type$ o = ($type$) vh.getAndBitwiseOrAcquire(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + $type$ o = ($type$) vh.getAndBitwiseOrAcquire(array, ci, VALUE_1); + }); - checkISE(() -> { - $type$ o = ($type$) vh.getAndBitwiseOrRelease(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + $type$ o = ($type$) vh.getAndBitwiseOrRelease(array, ci, VALUE_1); + }); - checkISE(() -> { - $type$ o = ($type$) vh.getAndBitwiseAnd(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + $type$ o = ($type$) vh.getAndBitwiseAnd(array, ci, VALUE_1); + }); - checkISE(() -> { - $type$ o = ($type$) vh.getAndBitwiseAndAcquire(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + $type$ o = ($type$) vh.getAndBitwiseAndAcquire(array, ci, VALUE_1); + }); - checkISE(() -> { - $type$ o = ($type$) vh.getAndBitwiseAndRelease(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + $type$ o = ($type$) vh.getAndBitwiseAndRelease(array, ci, VALUE_1); + }); - checkISE(() -> { - $type$ o = ($type$) vh.getAndBitwiseXor(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + $type$ o = ($type$) vh.getAndBitwiseXor(array, ci, VALUE_1); + }); - checkISE(() -> { - $type$ o = ($type$) vh.getAndBitwiseXorAcquire(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + $type$ o = ($type$) vh.getAndBitwiseXorAcquire(array, ci, VALUE_1); + }); - checkISE(() -> { - $type$ o = ($type$) vh.getAndBitwiseXorRelease(array, ci, VALUE_1); - }); + checkIOOBE(() -> { + $type$ o = ($type$) vh.getAndBitwiseXorRelease(array, ci, VALUE_1); + }); #end[Bitwise] + } } } } @@ -1420,7 +1161,6 @@ public class VarHandleTestByteArrayAs$Type$ extends VarHandleBaseByteArrayTest { checkISE(() -> { vh.setOpaque(array, ci, VALUE_1); }); - #if[CAS] checkISE(() -> { boolean r = vh.compareAndSet(array, ci, VALUE_1, VALUE_2); @@ -1466,7 +1206,6 @@ public class VarHandleTestByteArrayAs$Type$ extends VarHandleBaseByteArrayTest { $type$ o = ($type$) vh.getAndSetRelease(array, ci, VALUE_1); }); #end[CAS] - #if[AtomicAdd] checkISE(() -> { $type$ o = ($type$) vh.getAndAdd(array, ci, VALUE_1); @@ -1480,7 +1219,6 @@ public class VarHandleTestByteArrayAs$Type$ extends VarHandleBaseByteArrayTest { $type$ o = ($type$) vh.getAndAddRelease(array, ci, VALUE_1); }); #end[AtomicAdd] - #if[Bitwise] checkISE(() -> { $type$ o = ($type$) vh.getAndBitwiseOr(array, ci, VALUE_1); @@ -1527,320 +1265,15 @@ public class VarHandleTestByteArrayAs$Type$ extends VarHandleBaseByteArrayTest { VarHandle vh = vhs.s; byte[] array = bs.s; - int misalignmentAtZero = ByteBuffer.wrap(array).alignmentOffset(0, SIZE); - bs.fill((byte) 0xff); int length = array.length - SIZE + 1; for (int i = 0; i < length; i++) { - boolean iAligned = ((i + misalignmentAtZero) & (SIZE - 1)) == 0; - // Plain { vh.set(array, i, VALUE_1); $type$ x = ($type$) vh.get(array, i); assertEquals(x, VALUE_1, "get $type$ value"); } - - - if (iAligned) { - // Volatile - { - vh.setVolatile(array, i, VALUE_2); - $type$ x = ($type$) vh.getVolatile(array, i); - assertEquals(x, VALUE_2, "setVolatile $type$ value"); - } - - // Lazy - { - vh.setRelease(array, i, VALUE_1); - $type$ x = ($type$) vh.getAcquire(array, i); - assertEquals(x, VALUE_1, "setRelease $type$ value"); - } - - // Opaque - { - vh.setOpaque(array, i, VALUE_2); - $type$ x = ($type$) vh.getOpaque(array, i); - assertEquals(x, VALUE_2, "setOpaque $type$ value"); - } -#if[CAS] - - vh.set(array, i, VALUE_1); - - // Compare - { - boolean r = vh.compareAndSet(array, i, VALUE_1, VALUE_2); - assertEquals(r, true, "success compareAndSet $type$"); - $type$ x = ($type$) vh.get(array, i); - assertEquals(x, VALUE_2, "success compareAndSet $type$ value"); - } - - { - boolean r = vh.compareAndSet(array, i, VALUE_1, VALUE_3); - assertEquals(r, false, "failing compareAndSet $type$"); - $type$ x = ($type$) vh.get(array, i); - assertEquals(x, VALUE_2, "failing compareAndSet $type$ value"); - } - - { - $type$ r = ($type$) vh.compareAndExchange(array, i, VALUE_2, VALUE_1); - assertEquals(r, VALUE_2, "success compareAndExchange $type$"); - $type$ x = ($type$) vh.get(array, i); - assertEquals(x, VALUE_1, "success compareAndExchange $type$ value"); - } - - { - $type$ r = ($type$) vh.compareAndExchange(array, i, VALUE_2, VALUE_3); - assertEquals(r, VALUE_1, "failing compareAndExchange $type$"); - $type$ x = ($type$) vh.get(array, i); - assertEquals(x, VALUE_1, "failing compareAndExchange $type$ value"); - } - - { - $type$ r = ($type$) vh.compareAndExchangeAcquire(array, i, VALUE_1, VALUE_2); - assertEquals(r, VALUE_1, "success compareAndExchangeAcquire $type$"); - $type$ x = ($type$) vh.get(array, i); - assertEquals(x, VALUE_2, "success compareAndExchangeAcquire $type$ value"); - } - - { - $type$ r = ($type$) vh.compareAndExchangeAcquire(array, i, VALUE_1, VALUE_3); - assertEquals(r, VALUE_2, "failing compareAndExchangeAcquire $type$"); - $type$ x = ($type$) vh.get(array, i); - assertEquals(x, VALUE_2, "failing compareAndExchangeAcquire $type$ value"); - } - - { - $type$ r = ($type$) vh.compareAndExchangeRelease(array, i, VALUE_2, VALUE_1); - assertEquals(r, VALUE_2, "success compareAndExchangeRelease $type$"); - $type$ x = ($type$) vh.get(array, i); - assertEquals(x, VALUE_1, "success compareAndExchangeRelease $type$ value"); - } - - { - $type$ r = ($type$) vh.compareAndExchangeRelease(array, i, VALUE_2, VALUE_3); - assertEquals(r, VALUE_1, "failing compareAndExchangeRelease $type$"); - $type$ x = ($type$) vh.get(array, i); - assertEquals(x, VALUE_1, "failing compareAndExchangeRelease $type$ value"); - } - - { - boolean success = false; - for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) { - success = vh.weakCompareAndSetPlain(array, i, VALUE_1, VALUE_2); - if (!success) weakDelay(); - } - assertEquals(success, true, "success weakCompareAndSetPlain $type$"); - $type$ x = ($type$) vh.get(array, i); - assertEquals(x, VALUE_2, "success weakCompareAndSetPlain $type$ value"); - } - - { - boolean success = vh.weakCompareAndSetPlain(array, i, VALUE_1, VALUE_3); - assertEquals(success, false, "failing weakCompareAndSetPlain $type$"); - $type$ x = ($type$) vh.get(array, i); - assertEquals(x, VALUE_2, "failing weakCompareAndSetPlain $type$ value"); - } - - { - boolean success = false; - for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) { - success = vh.weakCompareAndSetAcquire(array, i, VALUE_2, VALUE_1); - if (!success) weakDelay(); - } - assertEquals(success, true, "success weakCompareAndSetAcquire $type$"); - $type$ x = ($type$) vh.get(array, i); - assertEquals(x, VALUE_1, "success weakCompareAndSetAcquire $type$"); - } - - { - boolean success = vh.weakCompareAndSetAcquire(array, i, VALUE_2, VALUE_3); - assertEquals(success, false, "failing weakCompareAndSetAcquire $type$"); - $type$ x = ($type$) vh.get(array, i); - assertEquals(x, VALUE_1, "failing weakCompareAndSetAcquire $type$ value"); - } - - { - boolean success = false; - for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) { - success = vh.weakCompareAndSetRelease(array, i, VALUE_1, VALUE_2); - if (!success) weakDelay(); - } - assertEquals(success, true, "success weakCompareAndSetRelease $type$"); - $type$ x = ($type$) vh.get(array, i); - assertEquals(x, VALUE_2, "success weakCompareAndSetRelease $type$"); - } - - { - boolean success = vh.weakCompareAndSetRelease(array, i, VALUE_1, VALUE_3); - assertEquals(success, false, "failing weakCompareAndSetRelease $type$"); - $type$ x = ($type$) vh.get(array, i); - assertEquals(x, VALUE_2, "failing weakCompareAndSetRelease $type$ value"); - } - - { - boolean success = false; - for (int c = 0; c < WEAK_ATTEMPTS && !success; c++) { - success = vh.weakCompareAndSet(array, i, VALUE_2, VALUE_1); - if (!success) weakDelay(); - } - assertEquals(success, true, "success weakCompareAndSet $type$"); - $type$ x = ($type$) vh.get(array, i); - assertEquals(x, VALUE_1, "success weakCompareAndSet $type$"); - } - - { - boolean success = vh.weakCompareAndSet(array, i, VALUE_2, VALUE_3); - assertEquals(success, false, "failing weakCompareAndSet $type$"); - $type$ x = ($type$) vh.get(array, i); - assertEquals(x, VALUE_1, "failing weakCompareAndSet $type$ value"); - } - - // Compare set and get - { - vh.set(array, i, VALUE_1); - - $type$ o = ($type$) vh.getAndSet(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndSet $type$"); - $type$ x = ($type$) vh.get(array, i); - assertEquals(x, VALUE_2, "getAndSet $type$ value"); - } - - { - vh.set(array, i, VALUE_1); - - $type$ o = ($type$) vh.getAndSetAcquire(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndSetAcquire $type$"); - $type$ x = ($type$) vh.get(array, i); - assertEquals(x, VALUE_2, "getAndSetAcquire $type$ value"); - } - - { - vh.set(array, i, VALUE_1); - - $type$ o = ($type$) vh.getAndSetRelease(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndSetRelease $type$"); - $type$ x = ($type$) vh.get(array, i); - assertEquals(x, VALUE_2, "getAndSetRelease $type$ value"); - } -#end[CAS] - -#if[AtomicAdd] - // get and add, add and get - { - vh.set(array, i, VALUE_1); - - $type$ o = ($type$) vh.getAndAdd(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndAdd $type$"); - $type$ x = ($type$) vh.get(array, i); - assertEquals(x, VALUE_1 + VALUE_2, "getAndAdd $type$ value"); - } - - { - vh.set(array, i, VALUE_1); - - $type$ o = ($type$) vh.getAndAddAcquire(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndAddAcquire $type$"); - $type$ x = ($type$) vh.get(array, i); - assertEquals(x, VALUE_1 + VALUE_2, "getAndAddAcquire $type$ value"); - } - - { - vh.set(array, i, VALUE_1); - - $type$ o = ($type$) vh.getAndAddRelease(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndAddRelease $type$"); - $type$ x = ($type$) vh.get(array, i); - assertEquals(x, VALUE_1 + VALUE_2, "getAndAddRelease $type$ value"); - } -#end[AtomicAdd] - -#if[Bitwise] - // get and bitwise or - { - vh.set(array, i, VALUE_1); - - $type$ o = ($type$) vh.getAndBitwiseOr(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndBitwiseOr $type$"); - $type$ x = ($type$) vh.get(array, i); - assertEquals(x, VALUE_1 | VALUE_2, "getAndBitwiseOr $type$ value"); - } - - { - vh.set(array, i, VALUE_1); - - $type$ o = ($type$) vh.getAndBitwiseOrAcquire(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndBitwiseOrAcquire $type$"); - $type$ x = ($type$) vh.get(array, i); - assertEquals(x, VALUE_1 | VALUE_2, "getAndBitwiseOrAcquire $type$ value"); - } - - { - vh.set(array, i, VALUE_1); - - $type$ o = ($type$) vh.getAndBitwiseOrRelease(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndBitwiseOrRelease $type$"); - $type$ x = ($type$) vh.get(array, i); - assertEquals(x, VALUE_1 | VALUE_2, "getAndBitwiseOrRelease $type$ value"); - } - - // get and bitwise and - { - vh.set(array, i, VALUE_1); - - $type$ o = ($type$) vh.getAndBitwiseAnd(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndBitwiseAnd $type$"); - $type$ x = ($type$) vh.get(array, i); - assertEquals(x, VALUE_1 & VALUE_2, "getAndBitwiseAnd $type$ value"); - } - - { - vh.set(array, i, VALUE_1); - - $type$ o = ($type$) vh.getAndBitwiseAndAcquire(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndBitwiseAndAcquire $type$"); - $type$ x = ($type$) vh.get(array, i); - assertEquals(x, VALUE_1 & VALUE_2, "getAndBitwiseAndAcquire $type$ value"); - } - - { - vh.set(array, i, VALUE_1); - - $type$ o = ($type$) vh.getAndBitwiseAndRelease(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndBitwiseAndRelease $type$"); - $type$ x = ($type$) vh.get(array, i); - assertEquals(x, VALUE_1 & VALUE_2, "getAndBitwiseAndRelease $type$ value"); - } - - // get and bitwise xor - { - vh.set(array, i, VALUE_1); - - $type$ o = ($type$) vh.getAndBitwiseXor(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndBitwiseXor $type$"); - $type$ x = ($type$) vh.get(array, i); - assertEquals(x, VALUE_1 ^ VALUE_2, "getAndBitwiseXor $type$ value"); - } - - { - vh.set(array, i, VALUE_1); - - $type$ o = ($type$) vh.getAndBitwiseXorAcquire(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndBitwiseXorAcquire $type$"); - $type$ x = ($type$) vh.get(array, i); - assertEquals(x, VALUE_1 ^ VALUE_2, "getAndBitwiseXorAcquire $type$ value"); - } - - { - vh.set(array, i, VALUE_1); - - $type$ o = ($type$) vh.getAndBitwiseXorRelease(array, i, VALUE_2); - assertEquals(o, VALUE_1, "getAndBitwiseXorRelease $type$"); - $type$ x = ($type$) vh.get(array, i); - assertEquals(x, VALUE_1 ^ VALUE_2, "getAndBitwiseXorRelease $type$ value"); - } -#end[Bitwise] - } } } @@ -1849,12 +1282,10 @@ public class VarHandleTestByteArrayAs$Type$ extends VarHandleBaseByteArrayTest { VarHandle vh = vhs.s; ByteBuffer array = bs.s; - int misalignmentAtZero = array.alignmentOffset(0, SIZE); - bs.fill((byte) 0xff); int length = array.limit() - SIZE + 1; for (int i = 0; i < length; i++) { - boolean iAligned = ((i + misalignmentAtZero) & (SIZE - 1)) == 0; + boolean iAligned = array.isDirect() ? ((i + array.alignmentOffset(0, SIZE)) & (SIZE - 1)) == 0 : false; // Plain { @@ -2169,15 +1600,13 @@ public class VarHandleTestByteArrayAs$Type$ extends VarHandleBaseByteArrayTest { VarHandle vh = vhs.s; ByteBuffer array = bs.s; - int misalignmentAtZero = array.alignmentOffset(0, SIZE); - ByteBuffer bb = ByteBuffer.allocate(SIZE); bb.order(MemoryMode.BIG_ENDIAN.isSet(vhs.memoryModes) ? ByteOrder.BIG_ENDIAN : ByteOrder.LITTLE_ENDIAN); bs.fill(bb.put$Type$(0, VALUE_2).array()); int length = array.limit() - SIZE + 1; for (int i = 0; i < length; i++) { - boolean iAligned = ((i + misalignmentAtZero) & (SIZE - 1)) == 0; + boolean iAligned = array.isDirect() ? ((i + array.alignmentOffset(0, SIZE)) & (SIZE - 1)) == 0 : false; $type$ v = MemoryMode.BIG_ENDIAN.isSet(vhs.memoryModes) ? rotateLeft(VALUE_2, (i % SIZE) << 3) diff --git a/test/jdk/java/nio/Buffer/Basic-X.java.template b/test/jdk/java/nio/Buffer/Basic-X.java.template index d26d3e3e622..4cd61ea8043 100644 --- a/test/jdk/java/nio/Buffer/Basic-X.java.template +++ b/test/jdk/java/nio/Buffer/Basic-X.java.template @@ -384,7 +384,7 @@ public class Basic$Type$ // unit size not a power of two catchIllegalArgument(b, () -> b.alignmentOffset(0, _us)); } else { - if (direct || us <= 8) { + if (direct || us == 1) { b.alignmentOffset(0, us); } else { // unit size > 8 with non-direct buffer @@ -394,12 +394,11 @@ public class Basic$Type$ } } - // Probe for long misalignment at index zero for a newly created buffer - ByteBuffer empty = - direct ? ByteBuffer.allocateDirect(0) : ByteBuffer.allocate(0); - int longMisalignmentAtZero = empty.alignmentOffset(0, 8); - if (direct) { + // Probe for long misalignment at index zero for a newly created buffer + ByteBuffer empty = ByteBuffer.allocateDirect(0); + int longMisalignmentAtZero = empty.alignmentOffset(0, 8); + // Freshly created direct byte buffers should be aligned at index 0 // for ref and primitive values (see Unsafe.allocateMemory) if (longMisalignmentAtZero != 0) { @@ -407,78 +406,67 @@ public class Basic$Type$ + " for ref and primitive values " + longMisalignmentAtZero); } - } else { - // For heap byte buffers misalignment may occur on 32-bit systems - // where Unsafe.ARRAY_BYTE_BASE_OFFSET % 8 == 4 and not 0 - // Note the GC will preserve alignment of the base address of the - // array - if (jdk.internal.misc.Unsafe.ARRAY_BYTE_BASE_OFFSET % 8 - != longMisalignmentAtZero) { - fail("Heap byte buffer misaligned at index 0" - + " for ref and primitive values " - + longMisalignmentAtZero); - } - } - // Ensure test buffer is correctly aligned at index 0 - if (b.alignmentOffset(0, 8) != longMisalignmentAtZero) - fail("Test input buffer not correctly aligned at index 0", b); + // Ensure test buffer is correctly aligned at index 0 + if (b.alignmentOffset(0, 8) != longMisalignmentAtZero) + fail("Test input buffer not correctly aligned at index 0", b); - // Test misalignment values - for (int us : new int[]{1, 2, 4, 8}) { - for (int i = 0; i < us * 2; i++) { - int am = b.alignmentOffset(i, us); - int expectedAm = (longMisalignmentAtZero + i) % us; + // Test misalignment values + for (int us : new int[]{1, 2, 4, 8}) { + for (int i = 0; i < us * 2; i++) { + int am = b.alignmentOffset(i, us); + int expectedAm = (longMisalignmentAtZero + i) % us; - if (am != expectedAm) { - String f = "b.alignmentOffset(%d, %d) == %d incorrect, expected %d"; - fail(String.format(f, i, us, am, expectedAm)); + if (am != expectedAm) { + String f = "b.alignmentOffset(%d, %d) == %d incorrect, expected %d"; + fail(String.format(f, i, us, am, expectedAm)); + } } } - } - // Created aligned slice to test against - int ap = 8 - longMisalignmentAtZero; - int al = b.limit() - b.alignmentOffset(b.limit(), 8); - ByteBuffer ab = b.position(ap).limit(al). - slice(); - if (ab.limit() == 0) { - fail("Test input buffer not sufficiently sized to cover" + - " an aligned region for all values", b); - } - if (ab.alignmentOffset(0, 8) != 0) - fail("Aligned test input buffer not correctly aligned at index 0", ab); + // Created aligned slice to test against + int ap = 8 - longMisalignmentAtZero; + int al = b.limit() - b.alignmentOffset(b.limit(), 8); + ByteBuffer ab = b.position(ap).limit(al). + slice(); + if (ab.limit() == 0) { + fail("Test input buffer not sufficiently sized to cover" + + " an aligned region for all values", b); + } + if (ab.alignmentOffset(0, 8) != 0) + fail("Aligned test input buffer not correctly aligned at index 0", ab); - for (int us : new int[]{1, 2, 4, 8}) { - for (int p = 1; p < 16; p++) { - int l = ab.limit() - p; + for (int us : new int[]{1, 2, 4, 8}) { + for (int p = 1; p < 16; p++) { + int l = ab.limit() - p; - ByteBuffer as = ab.slice().position(p).limit(l). - alignedSlice(us); + ByteBuffer as = ab.slice().position(p).limit(l). + alignedSlice(us); - ck(as, 0, as.position()); - ck(as, as.capacity(), as.limit()); - if (b.isDirect() != as.isDirect()) - fail("Lost direction", as); - if (b.isReadOnly() != as.isReadOnly()) - fail("Lost read-only", as); + ck(as, 0, as.position()); + ck(as, as.capacity(), as.limit()); + if (b.isDirect() != as.isDirect()) + fail("Lost direction", as); + if (b.isReadOnly() != as.isReadOnly()) + fail("Lost read-only", as); - if (as.alignmentOffset(0, us) != 0) - fail("Buffer not correctly aligned at index 0", as); + if (as.alignmentOffset(0, us) != 0) + fail("Buffer not correctly aligned at index 0", as); - if (as.alignmentOffset(as.limit(), us) != 0) - fail("Buffer not correctly aligned at limit", as); + if (as.alignmentOffset(as.limit(), us) != 0) + fail("Buffer not correctly aligned at limit", as); - int p_mod = ab.alignmentOffset(p, us); - int l_mod = ab.alignmentOffset(l, us); - // Round up position - p = (p_mod > 0) ? p + (us - p_mod) : p; - // Round down limit - l = l - l_mod; + int p_mod = ab.alignmentOffset(p, us); + int l_mod = ab.alignmentOffset(l, us); + // Round up position + p = (p_mod > 0) ? p + (us - p_mod) : p; + // Round down limit + l = l - l_mod; - int ec = l - p; - if (as.limit() != ec) { - fail("Buffer capacity incorrect, expected: " + ec, as); + int ec = l - p; + if (as.limit() != ec) { + fail("Buffer capacity incorrect, expected: " + ec, as); + } } } } diff --git a/test/jdk/java/nio/Buffer/BasicByte.java b/test/jdk/java/nio/Buffer/BasicByte.java index b3db0b0c105..05bf8e523bb 100644 --- a/test/jdk/java/nio/Buffer/BasicByte.java +++ b/test/jdk/java/nio/Buffer/BasicByte.java @@ -384,7 +384,7 @@ public class BasicByte // unit size not a power of two catchIllegalArgument(b, () -> b.alignmentOffset(0, _us)); } else { - if (direct || us <= 8) { + if (direct || us == 1) { b.alignmentOffset(0, us); } else { // unit size > 8 with non-direct buffer @@ -394,12 +394,11 @@ public class BasicByte } } - // Probe for long misalignment at index zero for a newly created buffer - ByteBuffer empty = - direct ? ByteBuffer.allocateDirect(0) : ByteBuffer.allocate(0); - int longMisalignmentAtZero = empty.alignmentOffset(0, 8); - if (direct) { + // Probe for long misalignment at index zero for a newly created buffer + ByteBuffer empty = ByteBuffer.allocateDirect(0); + int longMisalignmentAtZero = empty.alignmentOffset(0, 8); + // Freshly created direct byte buffers should be aligned at index 0 // for ref and primitive values (see Unsafe.allocateMemory) if (longMisalignmentAtZero != 0) { @@ -407,78 +406,67 @@ public class BasicByte + " for ref and primitive values " + longMisalignmentAtZero); } - } else { - // For heap byte buffers misalignment may occur on 32-bit systems - // where Unsafe.ARRAY_BYTE_BASE_OFFSET % 8 == 4 and not 0 - // Note the GC will preserve alignment of the base address of the - // array - if (jdk.internal.misc.Unsafe.ARRAY_BYTE_BASE_OFFSET % 8 - != longMisalignmentAtZero) { - fail("Heap byte buffer misaligned at index 0" - + " for ref and primitive values " - + longMisalignmentAtZero); - } - } - // Ensure test buffer is correctly aligned at index 0 - if (b.alignmentOffset(0, 8) != longMisalignmentAtZero) - fail("Test input buffer not correctly aligned at index 0", b); + // Ensure test buffer is correctly aligned at index 0 + if (b.alignmentOffset(0, 8) != longMisalignmentAtZero) + fail("Test input buffer not correctly aligned at index 0", b); - // Test misalignment values - for (int us : new int[]{1, 2, 4, 8}) { - for (int i = 0; i < us * 2; i++) { - int am = b.alignmentOffset(i, us); - int expectedAm = (longMisalignmentAtZero + i) % us; + // Test misalignment values + for (int us : new int[]{1, 2, 4, 8}) { + for (int i = 0; i < us * 2; i++) { + int am = b.alignmentOffset(i, us); + int expectedAm = (longMisalignmentAtZero + i) % us; - if (am != expectedAm) { - String f = "b.alignmentOffset(%d, %d) == %d incorrect, expected %d"; - fail(String.format(f, i, us, am, expectedAm)); + if (am != expectedAm) { + String f = "b.alignmentOffset(%d, %d) == %d incorrect, expected %d"; + fail(String.format(f, i, us, am, expectedAm)); + } } } - } - // Created aligned slice to test against - int ap = 8 - longMisalignmentAtZero; - int al = b.limit() - b.alignmentOffset(b.limit(), 8); - ByteBuffer ab = b.position(ap).limit(al). - slice(); - if (ab.limit() == 0) { - fail("Test input buffer not sufficiently sized to cover" + - " an aligned region for all values", b); - } - if (ab.alignmentOffset(0, 8) != 0) - fail("Aligned test input buffer not correctly aligned at index 0", ab); + // Created aligned slice to test against + int ap = 8 - longMisalignmentAtZero; + int al = b.limit() - b.alignmentOffset(b.limit(), 8); + ByteBuffer ab = b.position(ap).limit(al). + slice(); + if (ab.limit() == 0) { + fail("Test input buffer not sufficiently sized to cover" + + " an aligned region for all values", b); + } + if (ab.alignmentOffset(0, 8) != 0) + fail("Aligned test input buffer not correctly aligned at index 0", ab); - for (int us : new int[]{1, 2, 4, 8}) { - for (int p = 1; p < 16; p++) { - int l = ab.limit() - p; + for (int us : new int[]{1, 2, 4, 8}) { + for (int p = 1; p < 16; p++) { + int l = ab.limit() - p; - ByteBuffer as = ab.slice().position(p).limit(l). - alignedSlice(us); + ByteBuffer as = ab.slice().position(p).limit(l). + alignedSlice(us); - ck(as, 0, as.position()); - ck(as, as.capacity(), as.limit()); - if (b.isDirect() != as.isDirect()) - fail("Lost direction", as); - if (b.isReadOnly() != as.isReadOnly()) - fail("Lost read-only", as); + ck(as, 0, as.position()); + ck(as, as.capacity(), as.limit()); + if (b.isDirect() != as.isDirect()) + fail("Lost direction", as); + if (b.isReadOnly() != as.isReadOnly()) + fail("Lost read-only", as); - if (as.alignmentOffset(0, us) != 0) - fail("Buffer not correctly aligned at index 0", as); + if (as.alignmentOffset(0, us) != 0) + fail("Buffer not correctly aligned at index 0", as); - if (as.alignmentOffset(as.limit(), us) != 0) - fail("Buffer not correctly aligned at limit", as); + if (as.alignmentOffset(as.limit(), us) != 0) + fail("Buffer not correctly aligned at limit", as); - int p_mod = ab.alignmentOffset(p, us); - int l_mod = ab.alignmentOffset(l, us); - // Round up position - p = (p_mod > 0) ? p + (us - p_mod) : p; - // Round down limit - l = l - l_mod; + int p_mod = ab.alignmentOffset(p, us); + int l_mod = ab.alignmentOffset(l, us); + // Round up position + p = (p_mod > 0) ? p + (us - p_mod) : p; + // Round down limit + l = l - l_mod; - int ec = l - p; - if (as.limit() != ec) { - fail("Buffer capacity incorrect, expected: " + ec, as); + int ec = l - p; + if (as.limit() != ec) { + fail("Buffer capacity incorrect, expected: " + ec, as); + } } } } diff --git a/test/jdk/java/nio/Buffer/BasicChar.java b/test/jdk/java/nio/Buffer/BasicChar.java index c1358847ad2..8d6cfd1eecf 100644 --- a/test/jdk/java/nio/Buffer/BasicChar.java +++ b/test/jdk/java/nio/Buffer/BasicChar.java @@ -527,18 +527,6 @@ public class BasicChar - - - - - - - - - - - - diff --git a/test/jdk/java/nio/Buffer/BasicDouble.java b/test/jdk/java/nio/Buffer/BasicDouble.java index d74fe3db0b7..4b1cde85a08 100644 --- a/test/jdk/java/nio/Buffer/BasicDouble.java +++ b/test/jdk/java/nio/Buffer/BasicDouble.java @@ -527,18 +527,6 @@ public class BasicDouble - - - - - - - - - - - - diff --git a/test/jdk/java/nio/Buffer/BasicFloat.java b/test/jdk/java/nio/Buffer/BasicFloat.java index e60fb7b203c..654dfe72fbe 100644 --- a/test/jdk/java/nio/Buffer/BasicFloat.java +++ b/test/jdk/java/nio/Buffer/BasicFloat.java @@ -527,18 +527,6 @@ public class BasicFloat - - - - - - - - - - - - diff --git a/test/jdk/java/nio/Buffer/BasicInt.java b/test/jdk/java/nio/Buffer/BasicInt.java index 2d0f591e892..4e1b8a237b4 100644 --- a/test/jdk/java/nio/Buffer/BasicInt.java +++ b/test/jdk/java/nio/Buffer/BasicInt.java @@ -527,18 +527,6 @@ public class BasicInt - - - - - - - - - - - - diff --git a/test/jdk/java/nio/Buffer/BasicLong.java b/test/jdk/java/nio/Buffer/BasicLong.java index 04807c3461b..02b30e879b6 100644 --- a/test/jdk/java/nio/Buffer/BasicLong.java +++ b/test/jdk/java/nio/Buffer/BasicLong.java @@ -527,18 +527,6 @@ public class BasicLong - - - - - - - - - - - - diff --git a/test/jdk/java/nio/Buffer/BasicShort.java b/test/jdk/java/nio/Buffer/BasicShort.java index bbf1b7a7fa4..22c6dd4b59d 100644 --- a/test/jdk/java/nio/Buffer/BasicShort.java +++ b/test/jdk/java/nio/Buffer/BasicShort.java @@ -527,18 +527,6 @@ public class BasicShort - - - - - - - - - - - -