< prev index next >

src/java.base/share/classes/java/lang/invoke/Invokers.java

Print this page
rev 47249 : 8187826: Avoid using reflection to bootstrap NamedFunctions
Reviewed-by: TBD


 594         NF_checkVarHandleExactType = 5,
 595         NF_LIMIT = 6;
 596 
 597     private static final @Stable NamedFunction[] NFS = new NamedFunction[NF_LIMIT];
 598 
 599     private static NamedFunction getFunction(byte func) {
 600         NamedFunction nf = NFS[func];
 601         if (nf != null) {
 602             return nf;
 603         }
 604         NFS[func] = nf = createFunction(func);
 605         // Each nf must be statically invocable or we get tied up in our bootstraps.
 606         assert(InvokerBytecodeGenerator.isStaticallyInvocable(nf));
 607         return nf;
 608     }
 609 
 610     private static NamedFunction createFunction(byte func) {
 611         try {
 612             switch (func) {
 613                 case NF_checkExactType:
 614                     return new NamedFunction(Invokers.class
 615                         .getDeclaredMethod("checkExactType", MethodHandle.class,  MethodType.class));
 616                 case NF_checkGenericType:
 617                     return new NamedFunction(Invokers.class
 618                         .getDeclaredMethod("checkGenericType", MethodHandle.class,  MethodType.class));
 619                 case NF_getCallSiteTarget:
 620                     return new NamedFunction(Invokers.class
 621                         .getDeclaredMethod("getCallSiteTarget", CallSite.class));
 622                 case NF_checkCustomized:
 623                     return new NamedFunction(Invokers.class
 624                         .getDeclaredMethod("checkCustomized", MethodHandle.class));
 625                 case NF_checkVarHandleGenericType:
 626                     return new NamedFunction(Invokers.class
 627                         .getDeclaredMethod("checkVarHandleGenericType", VarHandle.class, VarHandle.AccessDescriptor.class));
 628                 case NF_checkVarHandleExactType:
 629                     return new NamedFunction(Invokers.class
 630                         .getDeclaredMethod("checkVarHandleExactType", VarHandle.class, VarHandle.AccessDescriptor.class));
 631                 default:
 632                     throw newInternalError("Unknown function: " + func);
 633             }
 634         } catch (ReflectiveOperationException ex) {
 635             throw newInternalError(ex);
 636         }









 637     }
 638 
 639     private static class Lazy {
 640         private static final MethodHandle MH_asSpreader;
 641 
 642         static {
 643             try {
 644                 MH_asSpreader = IMPL_LOOKUP.findVirtual(MethodHandle.class, "asSpreader",
 645                         MethodType.methodType(MethodHandle.class, Class.class, int.class));
 646             } catch (ReflectiveOperationException ex) {
 647                 throw newInternalError(ex);
 648             }
 649         }
 650     }
 651 
 652     static {
 653         // The Holder class will contain pre-generated Invokers resolved
 654         // speculatively using MemberName.getFactory().resolveOrNull. However, that
 655         // doesn't initialize the class, which subtly breaks inlining etc. By forcing
 656         // initialization of the Holder class we avoid these issues.


 594         NF_checkVarHandleExactType = 5,
 595         NF_LIMIT = 6;
 596 
 597     private static final @Stable NamedFunction[] NFS = new NamedFunction[NF_LIMIT];
 598 
 599     private static NamedFunction getFunction(byte func) {
 600         NamedFunction nf = NFS[func];
 601         if (nf != null) {
 602             return nf;
 603         }
 604         NFS[func] = nf = createFunction(func);
 605         // Each nf must be statically invocable or we get tied up in our bootstraps.
 606         assert(InvokerBytecodeGenerator.isStaticallyInvocable(nf));
 607         return nf;
 608     }
 609 
 610     private static NamedFunction createFunction(byte func) {
 611         try {
 612             switch (func) {
 613                 case NF_checkExactType:
 614                     return getNamedFunction("checkExactType", MethodType.methodType(void.class, MethodHandle.class, MethodType.class));

 615                 case NF_checkGenericType:
 616                     return getNamedFunction("checkGenericType", MethodType.methodType(MethodHandle.class, MethodHandle.class, MethodType.class));

 617                 case NF_getCallSiteTarget:
 618                     return getNamedFunction("getCallSiteTarget", MethodType.methodType(MethodHandle.class, CallSite.class));

 619                 case NF_checkCustomized:
 620                     return getNamedFunction("checkCustomized", MethodType.methodType(void.class, MethodHandle.class));

 621                 case NF_checkVarHandleGenericType:
 622                     return getNamedFunction("checkVarHandleGenericType", MethodType.methodType(MethodHandle.class, VarHandle.class, VarHandle.AccessDescriptor.class));

 623                 case NF_checkVarHandleExactType:
 624                     return getNamedFunction("checkVarHandleExactType", MethodType.methodType(MethodHandle.class, VarHandle.class, VarHandle.AccessDescriptor.class));

 625                 default:
 626                     throw newInternalError("Unknown function: " + func);
 627             }
 628         } catch (ReflectiveOperationException ex) {
 629             throw newInternalError(ex);
 630         }
 631     }
 632 
 633     private static NamedFunction getNamedFunction(String name, MethodType type)
 634         throws ReflectiveOperationException
 635     {
 636         MemberName member = new MemberName(Invokers.class, name, type, REF_invokeStatic);
 637         return new NamedFunction(
 638                 MemberName.getFactory()
 639                         .resolveOrFail(REF_invokeStatic, member, Invokers.class, NoSuchMethodException.class));
 640     }
 641 
 642     private static class Lazy {
 643         private static final MethodHandle MH_asSpreader;
 644 
 645         static {
 646             try {
 647                 MH_asSpreader = IMPL_LOOKUP.findVirtual(MethodHandle.class, "asSpreader",
 648                         MethodType.methodType(MethodHandle.class, Class.class, int.class));
 649             } catch (ReflectiveOperationException ex) {
 650                 throw newInternalError(ex);
 651             }
 652         }
 653     }
 654 
 655     static {
 656         // The Holder class will contain pre-generated Invokers resolved
 657         // speculatively using MemberName.getFactory().resolveOrNull. However, that
 658         // doesn't initialize the class, which subtly breaks inlining etc. By forcing
 659         // initialization of the Holder class we avoid these issues.
< prev index next >