Constant descriptor resolved too soon during constant resolution?
jbvernee at xs4all.nl
Fri Aug 3 21:19:21 UTC 2018
Thanks for the response Maurizio!
> My feeling is that the BSM arg in bold above is wrong. That is a
> *live* method handle constant - e.g. of type MethodHandle, but that is
> not compatible with what the BSM expects (a ConstantDesc):
I have tested a few patches based on this observation, but I think that
the MethodHandle type is correct after all. The reason
`DynamicConstantDesc` needs `ConstantDesc`s as arguments is because it
needs to know how to put them in the constant pool. In other words, you
'expend' the descriptor when making a constant pool entry for it. You
are left with a constant pool entry that you can turn into a live type
(e.g. a MethodHandle), but that doesn't necessarily mean you can turn it
_back_ into a descriptor.
There are a few other dynamic bootstraps for `Enum` and `VarHandle`. The
`Enum` one expects `String`s, which are both descriptor and live object,
and the `VarHandle` ones, like `j.l.i.ConstantBoostraps::fieldVarhandle`
actually expect live types to be passed as arguments (`Class<?>` instead
of `ClassDesc`). Also, `DynamicConstantDesc::resolveConstantDesc`
resolves the descriptors before passing them to the bootstrap method.
Since `DynamicConstantDesc::constantBootstrap` actually requires
`ConstantDesc<?>`s as it's arguments, I think the real bug is in
public Optional<? extends ConstantDesc<ConstantDesc<T>>>
ConstantDesc<?> args = new
ConstantDesc<?>[bootstrapArgs.length + 5];
args = bootstrapMethod.owner().descriptorString();
args = bootstrapMethod.methodName();
args = bootstrapMethod.methodType().descriptorString();
args = constantName;
args = constantType.descriptorString();
System.arraycopy(bootstrapArgs, 0, args, 5,
Where the `args` array should still be turned into an array of
descriptors that wrap the descriptors that are already there. This
turn-into-descriptor already sneakily happens for the bootstrap method
and name and type, since those are all being turned into `String`, which
is it's own descriptor.
Brian told me in an earlier email that `ConstantDesc`s should also be
able to describe themselves, so I think the only missing puzzle piece
here is to add a method to `ConstantDesc` for that:
ConstantDesc<? extends ConstantDesc<T>> describeSelf();
And then call that in the `DynamicConstantDesc::describeConstable`
method, re-wrapping the descriptors:
ConstantDesc<?> bootstrapArgDescs =
// describe the descriptors
System.arraycopy(bootstrapArgDescs, 0, args, 5,
bootstrapArgs.length); // using the descriptors instead
And then I think you can also drop the `implements
Constable<ConstantDesc<...>>` from all the descriptor types.
I might look into making a patch for that later.
More information about the amber-dev