[jep-334] Asymmetric method types of MHD vs MH

Remi Forax forax at univ-mlv.fr
Tue Nov 20 15:20:46 UTC 2018


Hi Brian,
while i agree that the API is primarily a mirror the JVMS view and not the java.lang.invoke view,
one way to avoid that ambiguity is to rename methodType() to type() (as in NameAndType).

Rémi

----- Mail original -----
> De: "Brian Goetz" <brian.goetz at oracle.com>
> À: "Michael van Acken" <michael.van.acken at gmail.com>, "amber-dev" <amber-dev at openjdk.java.net>
> Envoyé: Mardi 20 Novembre 2018 14:28:06
> Objet: Re: [jep-334] Asymmetric method types of MHD vs MH

> Thanks for poking into these new APIs.  This is a good question.
> 
> Your mental model is a good first-order approximation, but it has some
> risk; in the event of conflict, XxDesc's classes loyalty will be to
> Constant_Xxx_info (the classfile format), rather than its live-type
> counterpart.
> 
> MethodHandle embeds the invocation mode (static, virtual, interface,
> special) in the MH itself, so that you can treat the receiver as just
> another parameter.  This is tremendously useful as the primary purpose
> of method handles is to be invoked; it collapse four invocation modes
> into one.
> 
> DirectMethodHandleDesc models the classfile structure of an invocation;
> the MethodRef_info/NameAndType/invocation bytecode -- as shown in your
> example:
> 
>     jshell> var mhd = (MethodHandleDesc)mh.describeConstable().get()
>     mhd ==> MethodHandleDesc[VIRTUAL/PrintStream::println()void]
> 
> I think what you're saying is: there is enough information here to correctly
> compose the type() -- for virtual/special/interface, curry the owner type on --
> and that this would provide alignment with the live MethodHandle behavior.
> 
> But, it would separate from the classfile Constant_MethodHandle_info behavior;
> what goes in the NameAndType here (for instance methods) is the receiver-less
> version.  Hence the conflict.
> 
> I think what is really going on here is that there are two types -- the MH type,
> and the lookup type; the latter is a property of the DMHDesc, while the former
> is a property of the MHDesc?
> 
> 
> On 11/20/2018 7:06 AM, Michael van Acken wrote:
>> While tracking down unexpected behavior in my compiler, I noticed that
>> MethodHandleDesc and MethodHandle differ in what they list in their
>> method type.  I was expecting that the MHD matches the MH, in that
>> the receiver of a virtual method is included in the parameter list.
>> Instead,
>> it is omitted.  (See below for a jshell example.)
>>
>> As a compiler writer, I find the MH's unified view on static and virtual
>> method types very helpful.  The current implementation's MHD class
>> does not mirror this view, which means I would have to special case the
>> method types for some operations.
>>
>> My mental model of the descriptor classes is, that they are one-to-one
>> symbolic representations of their handle counterparts.  I am very confused
>> by the difference in structure, with the receiver dropping out of the
>> method type.
>>
>>
>> |  Welcome to JShell -- Version 12-internal
>> |  For an introduction type: /help intro
>>
>> jshell> import java.lang.invoke.*
>>
>> jshell> import java.lang.constant.*
>>
>> jshell> var l = MethodHandles.lookup()
>> l ==>
>>
>> jshell> var mt = MethodType.methodType(Void.TYPE)
>> mt ==> ()void
>>
>> jshell> var mh = l.findVirtual(java.io.PrintStream.class, "println", mt)
>> mh ==> MethodHandle(PrintStream)void
>>
>> jshell> mh.type()
>> $6 ==> (PrintStream)void
>>
>> jshell> mh.type().parameterCount()
>> $7 ==> 1
>>
>> jshell> var mhd = (MethodHandleDesc)mh.describeConstable().get()
>> mhd ==> MethodHandleDesc[VIRTUAL/PrintStream::println()void]
>>
>> jshell> mhd.methodType()
>> $9 ==> MethodTypeDesc[()void]
>>
>> jshell> mhd.methodType().parameterCount()
>> $10 ==> 0
>>
>>
>> Regards,
> > Michael van Acken


More information about the amber-dev mailing list