src/share/classes/java/lang/invoke/CallSite.java
Index Unified diffs Context diffs Sdiffs Patch New Old Previous File Next File jdk Sdiff src/share/classes/java/lang/invoke

src/share/classes/java/lang/invoke/CallSite.java

Print this page
rev 10274 : 8050052: Small cleanups in java.lang.invoke code
Reviewed-by: ?
rev 10275 : imported patch invokers


  85 abstract
  86 public class CallSite {
  87     static { MethodHandleImpl.initStatics(); }
  88 
  89     // The actual payload of this call site:
  90     /*package-private*/
  91     MethodHandle target;    // Note: This field is known to the JVM.  Do not change.
  92 
  93     /**
  94      * Make a blank call site object with the given method type.
  95      * An initial target method is supplied which will throw
  96      * an {@link IllegalStateException} if called.
  97      * <p>
  98      * Before this {@code CallSite} object is returned from a bootstrap method,
  99      * it is usually provided with a more useful target method,
 100      * via a call to {@link CallSite#setTarget(MethodHandle) setTarget}.
 101      * @throws NullPointerException if the proposed type is null
 102      */
 103     /*package-private*/
 104     CallSite(MethodType type) {
 105         target = type.invokers().uninitializedCallSite();
 106     }
 107 
 108     /**
 109      * Make a call site object equipped with an initial target method handle.
 110      * @param target the method handle which will be the initial target of the call site
 111      * @throws NullPointerException if the proposed target is null
 112      */
 113     /*package-private*/
 114     CallSite(MethodHandle target) {
 115         target.type();  // null check
 116         this.target = target;
 117     }
 118 
 119     /**
 120      * Make a call site object equipped with an initial target method handle.
 121      * @param targetType the desired type of the call site
 122      * @param createTargetHook a hook which will bind the call site to the target method handle
 123      * @throws WrongMethodTypeException if the hook cannot be invoked on the required arguments,
 124      *         or if the target returned by the hook is not of the given {@code targetType}
 125      * @throws NullPointerException if the hook returns a null value


 200      * <p>
 201      * This method is equivalent to the following code:
 202      * <blockquote><pre>{@code
 203      * MethodHandle getTarget, invoker, result;
 204      * getTarget = MethodHandles.publicLookup().bind(this, "getTarget", MethodType.methodType(MethodHandle.class));
 205      * invoker = MethodHandles.exactInvoker(this.type());
 206      * result = MethodHandles.foldArguments(invoker, getTarget)
 207      * }</pre></blockquote>
 208      *
 209      * @return a method handle which always invokes this call site's current target
 210      */
 211     public abstract MethodHandle dynamicInvoker();
 212 
 213     /*non-public*/ MethodHandle makeDynamicInvoker() {
 214         MethodHandle getTarget = GET_TARGET.bindReceiver(this);
 215         MethodHandle invoker = MethodHandles.exactInvoker(this.type());
 216         return MethodHandles.foldArguments(invoker, getTarget);
 217     }
 218 
 219     private static final MethodHandle GET_TARGET;

 220     static {
 221         try {
 222             GET_TARGET = IMPL_LOOKUP.
 223                 findVirtual(CallSite.class, "getTarget", MethodType.methodType(MethodHandle.class));


 224         } catch (ReflectiveOperationException e) {
 225             throw newInternalError(e);
 226         }
 227     }
 228 
 229     /** This guy is rolled into the default target if a MethodType is supplied to the constructor. */
 230     /*package-private*/
 231     static Empty uninitializedCallSite() {
 232         throw new IllegalStateException("uninitialized call site");
 233     }
 234 











 235     // unsafe stuff:
 236     private static final long TARGET_OFFSET;
 237     static {
 238         try {
 239             TARGET_OFFSET = UNSAFE.objectFieldOffset(CallSite.class.getDeclaredField("target"));
 240         } catch (Exception ex) { throw new Error(ex); }
 241     }
 242 
 243     /*package-private*/
 244     void setTargetNormal(MethodHandle newTarget) {
 245         MethodHandleNatives.setCallSiteTargetNormal(this, newTarget);
 246     }
 247     /*package-private*/
 248     MethodHandle getTargetVolatile() {
 249         return (MethodHandle) UNSAFE.getObjectVolatile(this, TARGET_OFFSET);
 250     }
 251     /*package-private*/
 252     void setTargetVolatile(MethodHandle newTarget) {
 253         MethodHandleNatives.setCallSiteTargetVolatile(this, newTarget);
 254     }




  85 abstract
  86 public class CallSite {
  87     static { MethodHandleImpl.initStatics(); }
  88 
  89     // The actual payload of this call site:
  90     /*package-private*/
  91     MethodHandle target;    // Note: This field is known to the JVM.  Do not change.
  92 
  93     /**
  94      * Make a blank call site object with the given method type.
  95      * An initial target method is supplied which will throw
  96      * an {@link IllegalStateException} if called.
  97      * <p>
  98      * Before this {@code CallSite} object is returned from a bootstrap method,
  99      * it is usually provided with a more useful target method,
 100      * via a call to {@link CallSite#setTarget(MethodHandle) setTarget}.
 101      * @throws NullPointerException if the proposed type is null
 102      */
 103     /*package-private*/
 104     CallSite(MethodType type) {
 105         target = makeUninitializedCallSite(type);
 106     }
 107 
 108     /**
 109      * Make a call site object equipped with an initial target method handle.
 110      * @param target the method handle which will be the initial target of the call site
 111      * @throws NullPointerException if the proposed target is null
 112      */
 113     /*package-private*/
 114     CallSite(MethodHandle target) {
 115         target.type();  // null check
 116         this.target = target;
 117     }
 118 
 119     /**
 120      * Make a call site object equipped with an initial target method handle.
 121      * @param targetType the desired type of the call site
 122      * @param createTargetHook a hook which will bind the call site to the target method handle
 123      * @throws WrongMethodTypeException if the hook cannot be invoked on the required arguments,
 124      *         or if the target returned by the hook is not of the given {@code targetType}
 125      * @throws NullPointerException if the hook returns a null value


 200      * <p>
 201      * This method is equivalent to the following code:
 202      * <blockquote><pre>{@code
 203      * MethodHandle getTarget, invoker, result;
 204      * getTarget = MethodHandles.publicLookup().bind(this, "getTarget", MethodType.methodType(MethodHandle.class));
 205      * invoker = MethodHandles.exactInvoker(this.type());
 206      * result = MethodHandles.foldArguments(invoker, getTarget)
 207      * }</pre></blockquote>
 208      *
 209      * @return a method handle which always invokes this call site's current target
 210      */
 211     public abstract MethodHandle dynamicInvoker();
 212 
 213     /*non-public*/ MethodHandle makeDynamicInvoker() {
 214         MethodHandle getTarget = GET_TARGET.bindReceiver(this);
 215         MethodHandle invoker = MethodHandles.exactInvoker(this.type());
 216         return MethodHandles.foldArguments(invoker, getTarget);
 217     }
 218 
 219     private static final MethodHandle GET_TARGET;
 220     private static final MethodHandle THROW_UCS;
 221     static {
 222         try {
 223             GET_TARGET = IMPL_LOOKUP.
 224                 findVirtual(CallSite.class, "getTarget", MethodType.methodType(MethodHandle.class));
 225             THROW_UCS = IMPL_LOOKUP.
 226                 findStatic(CallSite.class, "uninitializedCallSite", MethodType.methodType(Object.class, Object[].class));
 227         } catch (ReflectiveOperationException e) {
 228             throw newInternalError(e);
 229         }
 230     }
 231 
 232     /** This guy is rolled into the default target if a MethodType is supplied to the constructor. */
 233     private static Object uninitializedCallSite(Object... ignore) {

 234         throw new IllegalStateException("uninitialized call site");
 235     }
 236 
 237     private MethodHandle makeUninitializedCallSite(MethodType targetType) {
 238         MethodType basicType = targetType.basicType();
 239         MethodHandle invoker = basicType.form().cachedMethodHandle(MethodTypeForm.MH_UNINIT_CS);
 240         if (invoker == null) {
 241             invoker = THROW_UCS.asType(basicType);
 242             invoker = basicType.form().setCachedMethodHandle(MethodTypeForm.MH_UNINIT_CS, invoker);
 243         }
 244         // unchecked view is OK since no values will be received or returned
 245         return invoker.viewAsType(targetType);
 246     }
 247 
 248     // unsafe stuff:
 249     private static final long TARGET_OFFSET;
 250     static {
 251         try {
 252             TARGET_OFFSET = UNSAFE.objectFieldOffset(CallSite.class.getDeclaredField("target"));
 253         } catch (Exception ex) { throw new Error(ex); }
 254     }
 255 
 256     /*package-private*/
 257     void setTargetNormal(MethodHandle newTarget) {
 258         MethodHandleNatives.setCallSiteTargetNormal(this, newTarget);
 259     }
 260     /*package-private*/
 261     MethodHandle getTargetVolatile() {
 262         return (MethodHandle) UNSAFE.getObjectVolatile(this, TARGET_OFFSET);
 263     }
 264     /*package-private*/
 265     void setTargetVolatile(MethodHandle newTarget) {
 266         MethodHandleNatives.setCallSiteTargetVolatile(this, newTarget);
 267     }


src/share/classes/java/lang/invoke/CallSite.java
Index Unified diffs Context diffs Sdiffs Patch New Old Previous File Next File