varHandle (variable handle) in java 9




Contents of page >
1) New API’s in java 9 for >
  • memory ordering,
  • Memory fences and
  • reachability-fence operation
So that referenced object and array elements remains strongly reachable.


2) These API’s in java 9 will be equivalent to >


The classes in java.util.concurrent package will be migrated from sun.misc.Unsafe to VarHandle in java 9.


3) These api will have following rule in java 9 >
  • Safety -  JVM cannot be placed in a corrupt memory state.
Example, objects field can be updated with instances field type (that can be casted to the field type), or
array element can only be accessed if index is not out of bound.
  • Integrity. Access to field of an object follows the same access rules as in case of getfield and putfield byte codes.
Also final field cannot be updated.
  • Performance. The performance must be similar to sun.misc.Unsafe operations
  • Usability. API better than the sun.misc.Unsafe.


4) What's the need for this in java 9?
These days concurrent and parallel programming is increasing by a lot.
Developers are not able to use Java constructs to arrange atomic operations.
Example - incrementing field count atomically. As of now this only can be done using >
  • AtomicInteger (this adds up space overhead and concurrency issues) or
  • use unsafe sun.misc.Unsafe API for JVM intrinsics. Intrinsics are faster, so they have become widely used, and are harmful to safety and portability.


5) What is varHandle (variable handle) in java 9?
  • varHandle is called variable handle in java 9.
  • A variable handle is a typed reference to a variable in java 9.
  • A variable handle supports read and write access to the variable under different access modes.


6) Following variable kinds are supported in java 9 >


Other variable kinds that may be considered to be supported are >
  • array views,
  • viewing a byte or char array as a long array, and
  • ByteBuffers (locations in off-heap regions).


7) varHandle (Variable handles) in java 9 require >
  • library enhancements,
  • JVM enhancements,
  • compiler support,
  • Minor updates to >
    • JLS (Java Language Specification) and
    • JVM Specification.
  • Minor language enhancements like >
    • enhance compile-time type checking and
    • complement existing syntax.


8) Variable handles in java 9 are modelled by a single abstract class >
java.lang.invoke.VarHandle
Each variable access mode is represented by a signature-polymorphic method.


When invoked on an associated VarHandle instance - If access modes won’t be applicable for certain variable types - It will throw UnsupportedOperationException.


9) The access modes categories >
  1. Read access modes -  reading a variable with volatile memory ordering effects.
  2. Write access modes - updating a variable with release memory ordering effects.
  3. Atomic update access modes - compare and set on a variable with volatile memory order effects for both read and writing.
  4. Numeric atomic update access modes - getAndAdd with plain memory order effects for writing and acquire memory order effects for reading.
  5. Bitwise atomic update access modes - getAndBitwise and with release memory order effects for writing and plain memory order effects for reading.


10) Creating varHandle (variable handle) in java 9 >
Methods to create VarHandle instances in java 9 for instance and static field variable are located in >
java.lang.invoke.MethodHandles.Lookup


VarHandle are created by a process of looking up the field within the associated receiving class.
Example -
lookup to obtain VarHandle for a field named i (of int type)
on a receiver class Foo >
class Foo {
   int i;
   ...
}
...
class Bar {
   static final VarHandle VH_FOO_FIELD_I;
   static {
       try {
        VH_FOO_FIELD_I = MethodHandles.lookup().
            in(Foo.class).
            findVarHandle(Foo.class, "i", int.class);
       } catch (Exception e) {
        throw new Error(e);
       }
   }
}


Access mode methods will throw UnsupportedOperationException when-
  • Write access mode methods for a VarHandle to a final field.
  • Numeric-based access mode methods (getAndAdd and addAndGet) for a reference variable type or a non-numeric type (such as boolean).
  • Bitwise-based access mode methods for a reference variable type, or float and double types.


11) Create VarHandle instances for array-based variable types in java 9 >
Methods to create VarHandle instances for array-based variable types in java 9 are located in>
java.lang.invoke.MethodHandles
And see arrayElement (getter and setter methods) in java.lang.invoke.MethodHandles class.
Example - create VarHandle to an array of int >
VarHandle intArrayHandle = MethodHandles.arrayElementVarHandle(int[].class);


Access mode methods will throw UnsupportedOperationException when >
  • Numeric-based access mode methods (getAndAdd and addAndGet) for an array component reference variable type or a non-numeric type (such as boolean)
  • Bitwise-based access mode methods for a reference variable type or the float and double types (the latter restriction may be removed in a future revision)


12) Create VarHandle instances for array-view-based variable types in java 9 >
Methods to create VarHandle instances for array-view-based variable types in java 9 are also located in >
java.lang.invoke.MethodHandles


Example - create VarHandle to view an array of byte as an unaligned array of long >


VarHandle longArrayViewHandle = MethodHandles.byteArrayViewVarHandle(
              long[].class, java.nio.ByteOrder.BIG_ENDIAN);


13) More about varHandle  in java 9 >
A MethodHandle can be produced for a VarHandle access mode method by using
MethodHandles.Lookup.findVirtual
For example - to produce a MethodHandle to the "compareAndSet" access mode for a particular variable kind and type in java 9 -
MethodHandle mhToVhCompareAndSet = MethodHandles.publicLookup().findVirtual(
       VarHandle.class,
       "compareAndSet",
       MethodType.methodType(boolean.class, Foo.class, int.class, int.class));


The MethodHandle can then be invoked with a variable kind and type compatible VarHandle instance as the first parameter:
mhToVhCompareAndSet.invokeExact(VH_FOO_FIELD_I, f, 0, 1);


Or mhToVhCompareAndSet can be bound to the VarHandle instance and then invoked -
MethodHandle mhToBoundVhCompareAndSet = mhToVhCompareAndSet
       .bindTo(VH_FOO_FIELD_I);
mhToBoundVhCompareAndSet.invokeExact(f, 0, 1);


Such a MethodHandle lookup using findVirtual will perform an asType transformation to adjust arguments and return values. The behaviour is equivalent to a MethodHandle produced using MethodHandles.varHandleInvoker, the analog of MethodHandles.invoker -
MethodHandle mhToVhCompareAndSet = MethodHandles.varHandleExactInvoker(
       VarHandle.AccessMode.COMPARE_AND_SET,
       MethodType.methodType(boolean.class, Foo.class, int.class, int.class));

mhToVhCompareAndSet.invokeExact(VH_FOO_FIELD_I, f, 0, 1);


VarHandle may be used in reflective scenarios by a wrapping class.
Example replacing the Unsafe usages within the >
  • FieldUpdater and Array in java.util.concurrent.Atomic packages.


14) Memory fences in java 9 >
  • Memory fenced operations are defined as static methods on the VarHandle class.
  • Memory fenced operations represents a minimal viable set for memory control.


/**
* Ensures that loads and stores before the fence will not be
* reordered with loads and stores after the fence.
*/
public static void fullFence() {}
/**
* Ensures that loads before the fence will not be reordered with
* loads and stores after the fence.
*/
public static void acquireFence() {}
/**
* Ensures that loads and stores before the fence will not be
* reordered with stores after the fence.
*/
public static void releaseFence() {}
/**
* Ensures that loads before the fence will not be reordered with
* loads after the fence.
*/
public static void loadLoadFence() {}
/**
* Ensures that stores before the fence will not be reordered with
* stores after the fence.
*/
public static void storeStoreFence() {}

15) Reachability fence in java 9>
The reachability fence is defined as a static method on java.lang.ref.Reference -


class java.lang.ref.Reference {
 public static void reachabilityFence(Object ref) {}
}


reachabilityFence method Ensures that the object referenced by the given reference remains, regardless of any prior actions of the program that might otherwise cause the object to become unreachable. Thus, referenced object is not reclaimable by garbage collection at least until after the invocation of this method.
Summary >
In this java tutorial we learned about Improve Locking performance in java 9.


Having any doubt? or you liked the tutorial! Please comment in below section.
Please express your love by liking JavaMadeSoEasy.com (JMSE) on facebook, following on google+ or Twitter.

RELATED LINKS>

Improve Locking performance in java 9

JVM logging system in Java 9 - Levels, tags, output, rotation, decoration


Labels: Core Java Java 9
eEdit
Must read for you :