Class HandleUtil
MethodHandles and VarHandles for reflection purposes.
All handles returned by methods in this class are fully privileged, meaning that they can perform any desired
operation on the target, as long as it makes sense. For example, it is allowed for a VarHandle returned by
this class to alter the value of a final field in a class.
For maximum performance, it is suggested to invoke this method once and cache the result in a static final
field. The JVM will then be able to inline the call and replace it with a standard opcode instruction.
- Since:
- 9.0.0
-
Nested Class Summary
Nested ClassesModifier and TypeClassDescriptionstatic enumIndicates which type of access needs to be performed on the method or field.static final classIndicates that an error occurred while attempting to invoke a specificMethodHandle.static interfaceRepresents the invocation to be carried out on the method handle.static interfaceRepresents the invocation to be carried out on the method handle.static final classHolds the names that are supposed to be used to locate the target.static final classIndicates that an error occurred while attempting to build aMethodHandleorVarHandle. -
Method Summary
Modifier and TypeMethodDescriptionstatic <R> Rinvoke(HandleUtil.MethodHandleInvoker<R> invoker) Attempts invocation of aMethodHandlewhich will return something, catching any exceptions.static voidAttempts invocation of aMethodHandlewhich does not return anything, catching any exceptions.static VarHandlelinkField(Class<?> owner, HandleUtil.AccessType accessType, HandleUtil.Names fieldNames, Class<?> type) Obtains a newVarHandleto the specified field with the givenHandleUtil.AccessType.static VarHandlelinkField(Class<?> owner, HandleUtil.AccessType accessType, String fieldName, Class<?> type) Obtains a newVarHandleto the specified field with the givenHandleUtil.AccessType.static MethodHandlelinkMethod(Class<?> type, HandleUtil.AccessType accessType, HandleUtil.Names methodNames, Class<?> returnType, Class<?>... arguments) Obtains a newMethodHandleto the specified method with the givenHandleUtil.AccessType.static MethodHandlelinkMethod(Class<?> type, HandleUtil.AccessType accessType, String methodName, Class<?> returnType, Class<?>... arguments) Obtains a newMethodHandleto the specified method with the givenHandleUtil.AccessType.
-
Method Details
-
linkMethod
public static MethodHandle linkMethod(Class<?> type, HandleUtil.AccessType accessType, String methodName, Class<?> returnType, Class<?>... arguments) Obtains a newMethodHandleto the specified method with the givenHandleUtil.AccessType.If more than one name needs to be specified, refer to
linkMethod(Class, AccessType, Names, Class, Class[])instead.Mapping resolution is automatic, meaning that the deobfuscation from one mapping set to the current one is automatically attempted.
- Parameters:
type- TheClasswhich defines the method to invoke.accessType- The type of access that the method handle should attemptmethodName- The name of the method that needs to be invoked. The name should be obfuscated.returnType- TheClassthat represents the return type of the target method.arguments- An array holding variousClasses, each representing the type of method parameter.- Returns:
- A
MethodHandlethat links to the method specified, if it exists. - Throws:
HandleUtil.UnableToLinkHandleException- If linkage fails due to no method found with the given name or the method was found, but it was unable to be accessed. The latter situation should never occur.- Since:
- 10.0.0
-
linkMethod
public static MethodHandle linkMethod(Class<?> type, HandleUtil.AccessType accessType, HandleUtil.Names methodNames, Class<?> returnType, Class<?>... arguments) Obtains a newMethodHandleto the specified method with the givenHandleUtil.AccessType.The various names will attempt resolution one at a time, and the first
MethodHandlethat links successfully will be returned.Mapping resolution is automatic, meaning that the deobfuscation from one mapping set to the current one is automatically attempted.
- Parameters:
type- TheClasswhich defines the method to invoke.accessType- The type of access that the method handle should attempt.methodNames- The various possible obfuscated names of the method that needs to be invoked.returnType- TheClassthat represents the return type of the target method.arguments- An array holding variousClasses, each representing the type of method parameter.- Returns:
- A
MethodHandlethat links to the method specified, if it exists. - Throws:
HandleUtil.UnableToLinkHandleException- If linkage fails due to no method found with the given names or a method was found, but it was unable to be accessed. The latter situation should never occur.- Since:
- 10.0.0
-
linkField
public static VarHandle linkField(Class<?> owner, HandleUtil.AccessType accessType, String fieldName, Class<?> type) Obtains a newVarHandleto the specified field with the givenHandleUtil.AccessType.If more than one name needs to be specified, refer to
linkField(Class, AccessType, Names, Class)instead.Mapping resolution is automatic, meaning that the deobfuscation from one mapping set to the current one is automatically attempted.
- Parameters:
owner- TheClasswhich defines the field that needs to be accessed.accessType- The type of access that the variable handle should attempt.fieldName- The name of the field that needs to be accessed. The name should be obfuscated.type- TheClassthat represents the type of the field that needs to be accessed.- Returns:
- A
VarHandlethat links to the field specified, if it exists. - Throws:
HandleUtil.UnableToLinkHandleException- If linkage fails due to no field found with the given name or the field was found, but it was unable to be accessed. The latter situation should never occur.- Since:
- 10.0.0
-
linkField
public static VarHandle linkField(Class<?> owner, HandleUtil.AccessType accessType, HandleUtil.Names fieldNames, Class<?> type) Obtains a newVarHandleto the specified field with the givenHandleUtil.AccessType.The various names will attempt resolution one at a time, and the first
VarHandlethat links successfully will be returned.Mapping resolution is automatic, meaning that the deobfuscation from one mapping set to the current one is automatically attempted.
- Parameters:
owner- TheClasswhich defines the field that needs to be accessed.accessType- The type of access that the variable handle should attempt.fieldNames- The various possible obfuscated names of the field that needs to be accessed.type- TheClassthat represents the type of the field that needs to be accessed.- Returns:
- A
VarHandlethat links to the field specified, if it exists. - Throws:
HandleUtil.UnableToLinkHandleException- If linkage fails due to no field found with the given names or a field was found, but it was unable to be accessed. The latter situation should never occur.- Since:
- 10.0.0
-
invoke
Attempts invocation of aMethodHandlewhich will return something, catching any exceptions.While the job of invoking the handle is still given to the caller, it is suggested to use this method as it automatically catches and rethrows exceptions as needed. See further in the documentation for more information on the exception contract of this method.
If the method to invoke returns nothing (i.e.
void), useinvokeVoid(MethodHandleVoidInvoker)instead.- Type Parameters:
R- The type of the value returned by the invocation of the method handle.- Parameters:
invoker- TheHandleUtil.MethodHandleInvokerresponsible for invoking the actual handle.- Returns:
- The result of the method invocation.
- Throws:
HandleUtil.FailedInvocationException- If the invocation fails due to a mismatch between the invocation in theinvokerand the one expected by the handle/RuntimeException- If any other exception occurs. Namely, if the exception is already a subclass ofRuntimeException, the exception will be rethrown as is. Otherwise, it will be wrapped in aRuntimeExceptionand rethrown.- Since:
- 9.0.0
-
invokeVoid
Attempts invocation of aMethodHandlewhich does not return anything, catching any exceptions.While the job of invoking the handle is still given to the caller, it is suggested to use this method as it automatically catches and rethrows exceptions as needed. See further in the documentation for more information on the exception contract of this method.
If the method to invoke returns something, use
invoke(MethodHandleInvoker)instead.- Parameters:
invoker- TheHandleUtil.MethodHandleVoidInvokerresponsible for invoking the actual handle.- Throws:
HandleUtil.FailedInvocationException- If the invocation fails due to a mismatch between the invocation in theinvokerand the one expected by the handle/RuntimeException- If any other exception occurs. Namely, if the exception is already a subclass ofRuntimeException, the exception will be rethrown as is. Otherwise, it will be wrapped in aRuntimeExceptionand rethrown.- Since:
- 9.0.0
-