如何在Jasmin中使用invokedynamic?

yan*_*kee 1 jvm jasmin invokedynamic

这里说:

Since 2.1 :
[..]
added the invokedynamic instruction
Run Code Online (Sandbox Code Playgroud)

因此,我认为可以用jasmin编写包含invokedynamics的指令代码.但是我找不到关于jasmin语法的任何文档,我只是想出了如何使用invokedynamic来获取Jasmin的VerifyErrors,而不是如何创建一个工作示例.

如何在Jasmin中正确使用该指令?

apa*_*gin 5

每个invokedynamic字节码应该引用相应的调用站点说明符(JVMS 6.5),它实际上是CONSTANT_InvokeDynamic类型的常量池条目(JVMS 4.4.10).

Jasmin(http://jasmin.sourceforge.net)不支持CONSTANT_InvokeDynamic,但Sable/jasmin确实支持.虽然invokedynamic在手写组装中使用是忘恩负义的工作.

以下是返回引用的动态方法示例System.out:

.class public HelloWorld
.super java/lang/Object

.method public <init>()V
   aload_0
   invokespecial java/lang/Object/<init>()V
   return
.end method

.method public static main([Ljava/lang/String;)V
   .limit stack 2
   .limit locals 1

   invokedynamic "getPrintStream" ()Ljava/io/PrintStream; HelloWorld/bootstrap(Ljava/lang/invoke/MethodHandles$Lookup;Ljava/lang/String;Ljava/lang/invoke/MethodType;)Ljava/lang/invoke/CallSite;()
   ldc "Hello, world"
   invokevirtual java/io/PrintStream/println(Ljava/lang/String;)V

   return
.end method

.method private static bootstrap(Ljava/lang/invoke/MethodHandles$Lookup;Ljava/lang/String;Ljava/lang/invoke/MethodType;)Ljava/lang/invoke/CallSite;
   .limit stack 6
   .limit locals 3

   new java/lang/invoke/ConstantCallSite
   dup

   aload_0
   ldc java/lang/System
   ldc "out"
   ldc java/io/PrintStream
   invokevirtual java/lang/invoke/MethodHandles$Lookup/findStaticGetter(Ljava/lang/Class;Ljava/lang/String;Ljava/lang/Class;)Ljava/lang/invoke/MethodHandle;

   invokespecial java/lang/invoke/ConstantCallSite/<init>(Ljava/lang/invoke/MethodHandle;)V

   areturn
.end method
Run Code Online (Sandbox Code Playgroud)

  • 调试之后,我想我需要在文件的末尾添加一个换行符,确实修复了OutOfMemoryError ...*facepalm*.无论如何,感谢您的意见:-). (2认同)