Constant descriptor resolved too soon during constant resolution?

Brian Goetz brian.goetz at oracle.com
Sat Aug 25 16:11:50 UTC 2018


I pushed some updates to the DCD factories (came at it from a different 
direction), and Vicente fixed the bugs you found.  So, give it another go?

On 8/2/2018 11:36 AM, Jorn Vernee wrote:
> Hello,
>
> I think I have stumbled upon a bug in the condy-folding branch (tip).
>
> This is the code to reproduce:
>
> ```
> import java.lang.constant.*;
> import static java.lang.constant.ConstantDescs.*;
>
> public class Main {
>
>     static final DirectMethodHandleDesc MHR_CONCAT = MethodHandleDesc.of(
>         DirectMethodHandleDesc.Kind.VIRTUAL,
>         CR_String,
>         "concat",
>         CR_String,
>         CR_String
>     );
>
>     public static void main(String[] args) throws Throwable {
>         ConstantDesc<String> d = 
> DynamicConstantDesc.<String>of(BSM_INVOKE).withArgs(MHR_CONCAT, 
> "Hello, ", "world!");
>         System.out.println(d); // <---- exception thrown here, on 
> resolution of `d2`
>     }
>
> }
> ```
>
> I'm wrapping a call to `ConstantBootstraps.invoke` together with a 
> method handle for `String.concat` and 2 constant arguments (a toy 
> example). The resolution should effectively call `"Hello, 
> ".concat("world!")`. Please note that I'm not resolving the result 
> string here though, but I'm resolving the descriptor itself. While 
> resolving the descriptor `d` an exception is thrown:
>
> ```
> Exception in thread "main" java.lang.BootstrapMethodError: bootstrap 
> method initialization exception
>         at 
> java.base/java.lang.invoke.BootstrapMethodInvoker.invoke(BootstrapMethodInvoker.java:253)
>         at 
> java.base/java.lang.invoke.ConstantBootstraps.makeConstant(ConstantBootstraps.java:71)
>         at 
> java.base/java.lang.invoke.MethodHandleNatives.linkDynamicConstantImpl(MethodHandleNatives.java:314)
>         at 
> java.base/java.lang.invoke.MethodHandleNatives.linkDynamicConstant(MethodHandleNatives.java:306)
>         at Main.main(Main.java:18)
> Caused by: java.lang.ClassCastException: Cannot cast 
> java.lang.invoke.DirectMethodHandle to java.lang.constant.ConstantDesc
>         at java.base/java.lang.Class.cast(Class.java:3613)
>         at 
> java.base/java.lang.invoke.BootstrapMethodInvoker.invokeWithManyArguments(BootstrapMethodInvoker.java:350)
>         at 
> java.base/java.lang.invoke.BootstrapMethodInvoker.invoke(BootstrapMethodInvoker.java:195)
>         ... 4 more
> ```
>
> This puzzled me for a while, but I _think_ the cause is that the 
> `MHR_CONCAT` descriptor is being resolved into a `DirectMethodHandle` 
> too early during resolution? Oddly enough, when using 
> `Intrinsics.ldc(d)` to resolve the result string, the program 
> completes successfully, and I can print the resulting string. The 
> following version also works as expected:
>
> ```
>     ConstantDesc<String> d = DynamicConstantDesc.of(
>         BSM_INVOKE, DEFAULT_NAME, CR_Object, new 
> ConstantDesc<?>[]{MHR_CONCAT, "Hello, ", "world!"}); // No folding 
> here, because the array is not a constant (?)
>     System.out.println(d); // This one is OK
> ```
>
> And it prints: 
> `DynamicConstantDesc[ConstantBootstraps::invoke(MethodHandleDesc[VIRTUAL/String::concat(String)String],Hello, 
> ,world!)Object]`. As far as I can tell these 2 snippets should behave 
> the same (the generated bytecode is quite different though), so I 
> think this is a bug?
>
> Is there a flag to temporarily turn off folding? I'm not aware of any 
> javac equivalent of `-XX:+PrintFlagsFinal`, so I don't have a way to 
> find out about experimental flags.
>
> Also, I hope this is the right place to post bug reports, JBS doesn't 
> seem to cover amber, and I've seen a few people reporting bugs on 
> other mailing lists, but I'd expect more people to be doing that, so 
> maybe I'm in the wrong place?
>
> Best regards,
> Jorn Vernee



More information about the amber-dev mailing list