Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Replace bridge methods with filtered methods in Painless #88100

Merged
merged 4 commits into from
Jul 5, 2022

Conversation

jdconrad
Copy link
Contributor

The invokedynamic instruction does not perfectly follow the Painless casting model opting to add bridge methods where necessary to ensure symmetric behavior between compile-time and run-time casting using boxed types. This change replaces the specialized class loader and bridge methods using filtered method handles instead. This reduces the overall complexity of runtime casting.

@jdconrad jdconrad added :Core/Infra/Scripting Scripting abstractions, Painless, and Mustache >refactoring labels Jun 28, 2022
@elasticmachine elasticmachine added the Team:Core/Infra Meta label for core/infra team label Jun 28, 2022
@elasticmachine
Copy link
Collaborator

Pinging @elastic/es-core-infra (Team:Core/Infra)

Copy link
Member

@rjernst rjernst left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looks fine as is. Mostly just nits and one suggestion on reducing duplication.

@@ -146,6 +146,14 @@ private ArrayLengthHelper() {}
/** factory for arraylength MethodHandle (intrinsic) from Java 9 (pkg-private for tests) */
static final MethodHandle JAVA9_ARRAY_LENGTH_MH_FACTORY;

public static final MethodHandle DEF_TO_B_BYTE_IMPLICIT_HANDLE;
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Maybe be more explicit in the name, use "BOXED" rather than "B". Another thought on the naming is maybe HANDLE is not needed (we don't have it on any of the other method handles here). So as an example:

DEF_TO_BOXED_BYTE_IMPLICIT_CAST

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Done.

for (int typeParameterCount = 0; typeParameterCount < javaMethod.getParameterTypes().length; ++typeParameterCount) {
Class<?> typeParameter = javaMethod.getParameterTypes()[typeParameterCount];

if (typeParameter == Byte.class) {
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It seems like there are enough cases here that you could reduce a lot of boilerplate by having Map<Class<?>, MethodHandle> instead of individual constants, and then the code here wouldn't need a chain of if/else. So instead of Def.DEF_TO_xxx you might have Def.IMPLICIT_BOXED_CASTS.get(typeParameter)

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Done.

@jdconrad
Copy link
Contributor Author

jdconrad commented Jul 5, 2022

@rjernst Thanks for the review. Will commit as soon as CI passes.

@jdconrad jdconrad merged commit 7234730 into elastic:master Jul 5, 2022
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
:Core/Infra/Scripting Scripting abstractions, Painless, and Mustache >refactoring Team:Core/Infra Meta label for core/infra team v8.4.0
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants