/* * Copyright (c) 2017, Oracle and/or its affiliates. All rights reserved. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * * This code is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License version 2 only, as * published by the Free Software Foundation. Oracle designates this * particular file as subject to the "Classpath" exception as provided * by Oracle in the LICENSE file that accompanied this code. * * This code is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License * version 2 for more details (a copy is included in the LICENSE file that * accompanied this code). * * You should have received a copy of the GNU General Public License version * 2 along with this work; if not, write to the Free Software Foundation, * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. * * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA * or visit www.oracle.com if you need additional information or have any * questions. */ package java.lang.invoke; import java.lang.constant.Constable; import java.lang.constant.ConstantDesc; import java.lang.invoke.AbstractBootstrapCallInfo.*; import java.lang.invoke.MethodHandles.Lookup; import java.util.List; import java.util.Objects; import sun.invoke.util.Wrapper; import static java.lang.invoke.BootstrapMethodInvoker.invokeCommon; /** * An interface providing full static information about a particular * call to a * bootstrap method of an * dynamic call site or dynamic constant. * This information includes the bootstrap method itself, the associated * name and type, and any associated static arguments. *
* If a bootstrap method declares exactly two arguments, and is * not of variable arity, then it is fed only two arguments by * the JVM, the {@linkplain Lookup lookup object} and an instance * of {@code BootstrapCallInfo} which supplies the rest of the * information about the call. *
* The API for accessing the static arguments allows the bootstrap * method to reorder the resolution (in the constant pool) of the * static arguments, and to catch errors resulting from the resolution. * This mode of evaluation pulls bootstrap parameters from * the JVM under control of the bootstrap method, as opposed to * the JVM pushing parameters to a bootstrap method * by resolving them all before the bootstrap method is called. * @apiNote *
* The {@linkplain Lookup lookup object} is not included in this * bundle of information, so as not to obscure the access control * logic of the program. * In cases where there are many thousands of parameters, it may * be preferable to pull their resolved values, either singly or in * batches, rather than wait until all of them have been resolved * before a constant or call site can be used. *
* A push mode bootstrap method can be adapted to a pull mode * bootstrap method, and vice versa. For example, this generic * adapter pops a push-mode bootstrap method from the beginning * of the static argument list, eagerly resolves all the remaining * static arguments, and invokes the popped method in push mode. * The callee has no way of telling that it was not called directly * from the JVM. *
* * @param{@code static Object genericBSM(Lookup lookup, BootstrapCallInfo
* After a normal return from {@link #argument(int)} or a present * value is reported from {@link #argument(int,Object)}, this method * must always return true. *
* If this method returns {@code false}, nothing in particular
* can be inferred, since the query only concerns the internal
* logic of the {@code BootstrapCallInfo} object which ensures that a
* successful query to a constant will always remain successful.
* The only way to force a permanent decision about whether
* a static argument is available is to call {@link #argument(int)} and
* be ready for an exception if the constant is unavailable.
* @param index which constant to select
* @return {@code true} if the selected static argument is known by
* this object to be present, {@code false} if it is known
* not to be present or
*/
boolean argumentIsPresent(int index);
/// Views
/**
* Create a view on the static arguments as a {@link List} view.
* Any request for a static argument through this view will
* force resolution, and may therefore cause a {@code LinkageError}.
* @return a {@code List} view on the static arguments which will force resolution
*/
default List
* @apiNote
* This method behaves like the following but may be more optimal:
*
* @apiNote
* This method behaves like the following but may be more optimal:
*
* @apiNote
* This method behaves like the following but may be more optimal:
*
*
* @param handle the bootstrap method handle to be invoked on the static arguments
* @param lookup the lookup
* @param name the name associated with the constant or call site being linked
* @param type the type associated with the constant or call site being linked
* @param staticArgs the static argument list
* @return the result of invocation
* @throws Throwable if an error occurs when resolving the constants from
* the bootstrap call descriptor or invoking the method handle
*/
static Object invokeWithMetadata(MethodHandle handle,
MethodHandles.Lookup lookup,
String name,
TypeDescriptor type,
List{@code
* ArrayList
*
* @param handle the bootstrap method handle to be invoked on the static arguments
* @param lookup the lookup
* @param name the name associated with the constant or call site being linked
* @param type the type associated with the constant or call site being linked
* @param staticArgs the static argument list
* @return the result of invocation
* @throws Throwable if an error occurs when resolving the constants from
* the bootstrap call descriptor or invoking the method handle
*/
static Object invokeWithMetadata(MethodHandle handle,
MethodHandles.Lookup lookup,
String name,
TypeDescriptor type,
Object... staticArgs)
throws Throwable {
Objects.requireNonNull(lookup);
Objects.requireNonNull(staticArgs);
return invokeCommon(handle, lookup, name, type, staticArgs, null);
}
/**
* Invoke a bootstrap method handle with arguments obtained by resolving
* the sequence of constants supplied by a given bootstrap call descriptor,
* {@code bci}.
* The first argument to the method will be {@code lookup}.
* The second argument will be the invocation name of {@code bci}.
* The third argument will be the invocation type of {@code bci}.
* The fourth and subsequent arguments (if any) will be the resolved
* constants, in order, supplied by {@code bci}.
* {@code
* ArrayList
*
* @param handle the bootstrap method handle to be invoked with resolved
* constants supplied by {@code bci}
* @param lookup the lookup
* @param bsci the bootstrap call descriptor
* @return the result of invocation
* @throws Throwable if an error occurs when resolving the constants from
* the bootstrap call descriptor or invoking the method handle
*/
static Object invokeWithMetadata(MethodHandle handle,
MethodHandles.Lookup lookup,
BootstrapCallInfo> bsci)
throws Throwable {
Objects.requireNonNull(lookup);
return invokeCommon(handle, lookup, bsci.invocationName(), bsci.invocationType(), AbstractBootstrapCallInfo.maybeShareArguments(bsci), bsci.argumentList());
}
/**
* Convert the result returned by a bootstrap method to the class
* required by the bootstrap method's {@code invocationType}.
*
* @param bsci the bootstrap call descriptor
* @param result the result to be converted
* @param {@code
* ArrayList