nashorn/src/jdk/nashorn/internal/runtime/linker/NashornBottomLinker.java
changeset 24719 f726e9d67629
parent 22669 75563515567f
child 24778 2ff5d7041566
equal deleted inserted replaced
23083:8c74590d5df1 24719:f726e9d67629
    42 import jdk.internal.dynalink.linker.GuardingDynamicLinker;
    42 import jdk.internal.dynalink.linker.GuardingDynamicLinker;
    43 import jdk.internal.dynalink.linker.GuardingTypeConverterFactory;
    43 import jdk.internal.dynalink.linker.GuardingTypeConverterFactory;
    44 import jdk.internal.dynalink.linker.LinkRequest;
    44 import jdk.internal.dynalink.linker.LinkRequest;
    45 import jdk.internal.dynalink.linker.LinkerServices;
    45 import jdk.internal.dynalink.linker.LinkerServices;
    46 import jdk.internal.dynalink.support.Guards;
    46 import jdk.internal.dynalink.support.Guards;
       
    47 import jdk.nashorn.internal.codegen.types.Type;
    47 import jdk.nashorn.internal.runtime.Context;
    48 import jdk.nashorn.internal.runtime.Context;
    48 import jdk.nashorn.internal.runtime.JSType;
    49 import jdk.nashorn.internal.runtime.JSType;
    49 import jdk.nashorn.internal.runtime.ScriptRuntime;
    50 import jdk.nashorn.internal.runtime.ScriptRuntime;
       
    51 import jdk.nashorn.internal.runtime.UnwarrantedOptimismException;
    50 
    52 
    51 /**
    53 /**
    52  * Nashorn bottom linker; used as a last-resort catch-all linker for all linking requests that fall through all other
    54  * Nashorn bottom linker; used as a last-resort catch-all linker for all linking requests that fall through all other
    53  * linkers (see how {@link Bootstrap} class configures the dynamic linker in its static initializer). It will throw
    55  * linkers (see how {@link Bootstrap} class configures the dynamic linker in its static initializer). It will throw
    54  * appropriate ECMAScript errors for attempts to invoke operations on {@code null}, link no-op property getters and
    56  * appropriate ECMAScript errors for attempts to invoke operations on {@code null}, link no-op property getters and
   102                 final MethodType callType = desc.getMethodType();
   104                 final MethodType callType = desc.getMethodType();
   103                 // 'callee' and 'thiz' passed from script + actual arguments
   105                 // 'callee' and 'thiz' passed from script + actual arguments
   104                 if (callType.parameterCount() != m.getParameterCount() + 2) {
   106                 if (callType.parameterCount() != m.getParameterCount() + 2) {
   105                     throw typeError("no.method.matches.args", ScriptRuntime.safeToString(self));
   107                     throw typeError("no.method.matches.args", ScriptRuntime.safeToString(self));
   106                 }
   108                 }
   107                 return new GuardedInvocation(
   109                 return Bootstrap.asTypeSafeReturn(new GuardedInvocation(
   108                         // drop 'thiz' passed from the script.
   110                         // drop 'thiz' passed from the script.
   109                         MH.dropArguments(desc.getLookup().unreflect(m), 1, callType.parameterType(1)),
   111                         MH.dropArguments(desc.getLookup().unreflect(m), 1, callType.parameterType(1)),
   110                         Guards.getInstanceOfGuard(m.getDeclaringClass())).asType(callType);
   112                         Guards.getInstanceOfGuard(m.getDeclaringClass())), linkerServices, desc);
   111             }
   113             }
   112             if(BeansLinker.isDynamicMethod(self)) {
   114             if(BeansLinker.isDynamicMethod(self)) {
   113                 throw typeError("no.method.matches.args", ScriptRuntime.safeToString(self));
   115                 throw typeError("no.method.matches.args", ScriptRuntime.safeToString(self));
   114             }
   116             }
   115             throw typeError("not.a.function", ScriptRuntime.safeToString(self));
   117             throw typeError("not.a.function", ScriptRuntime.safeToString(self));
   116         case "callMethod":
   118         case "callMethod":
   117         case "getMethod":
   119         case "getMethod":
   118             throw typeError("no.such.function", getArgument(linkRequest), ScriptRuntime.safeToString(self));
   120             throw typeError("no.such.function", getArgument(linkRequest), ScriptRuntime.safeToString(self));
   119         case "getProp":
   121         case "getProp":
   120         case "getElem":
   122         case "getElem":
       
   123             if(NashornCallSiteDescriptor.isOptimistic(desc)) {
       
   124                 throw new UnwarrantedOptimismException(UNDEFINED, NashornCallSiteDescriptor.getProgramPoint(desc), Type.OBJECT);
       
   125             }
   121             if (desc.getOperand() != null) {
   126             if (desc.getOperand() != null) {
   122                 return getInvocation(EMPTY_PROP_GETTER, self, linkerServices, desc);
   127                 return getInvocation(EMPTY_PROP_GETTER, self, linkerServices, desc);
   123             }
   128             }
   124             return getInvocation(EMPTY_ELEM_GETTER, self, linkerServices, desc);
   129             return getInvocation(EMPTY_ELEM_GETTER, self, linkerServices, desc);
   125         case "setProp":
   130         case "setProp":
   149      * @throws Exception if something goes wrong
   154      * @throws Exception if something goes wrong
   150      */
   155      */
   151     private static GuardedInvocation convertToTypeNoCast(final Class<?> sourceType, final Class<?> targetType) throws Exception {
   156     private static GuardedInvocation convertToTypeNoCast(final Class<?> sourceType, final Class<?> targetType) throws Exception {
   152         final MethodHandle mh = CONVERTERS.get(targetType);
   157         final MethodHandle mh = CONVERTERS.get(targetType);
   153         if (mh != null) {
   158         if (mh != null) {
   154             return new GuardedInvocation(mh, null);
   159             return new GuardedInvocation(mh);
   155         }
   160         }
   156 
   161 
   157         return null;
   162         return null;
   158     }
   163     }
   159 
   164 
   160     private static GuardedInvocation getInvocation(final MethodHandle handle, final Object self, final LinkerServices linkerServices, final CallSiteDescriptor desc) {
   165     private static GuardedInvocation getInvocation(final MethodHandle handle, final Object self, final LinkerServices linkerServices, final CallSiteDescriptor desc) {
   161         return Bootstrap.asType(new GuardedInvocation(handle, Guards.getClassGuard(self.getClass())), linkerServices, desc);
   166         return Bootstrap.asTypeSafeReturn(new GuardedInvocation(handle, Guards.getClassGuard(self.getClass())), linkerServices, desc);
   162     }
   167     }
   163 
   168 
   164     // Used solely in an assertion to figure out if the object we get here is something we in fact expect. Objects
   169     // Used solely in an assertion to figure out if the object we get here is something we in fact expect. Objects
   165     // linked by NashornLinker should never reach here.
   170     // linked by NashornLinker should never reach here.
   166     private static boolean isExpectedObject(final Object obj) {
   171     private static boolean isExpectedObject(final Object obj) {