Java JVM验证错误';常量池中的非法类型';
我目前正在编写自己的编译器,并尝试编译以下代码:Java JVM验证错误';常量池中的非法类型';,java,jvm,java-bytecode-asm,Java,Jvm,Java Bytecode Asm,我目前正在编写自己的编译器,并尝试编译以下代码: List[String] list = List("a", "b", "c", "d") list stream map((String s) => s.toUpperCase()) System out println list 编译器在解析、链接或编译代码时没有问题,但在执行代码时,JVM会抛出以下错误: java.lang.VerifyError: Illegal type at constant pool entry 40 in
List[String] list = List("a", "b", "c", "d")
list stream map((String s) => s.toUpperCase())
System out println list
编译器在解析、链接或编译代码时没有问题,但在执行代码时,JVM会抛出以下错误:
java.lang.VerifyError: Illegal type at constant pool entry 40 in class dyvil.test.Main
Exception Details:
Location:
dyvil/test/Main.main([Ljava/lang/String;)V @29: invokevirtual
Reason:
Constant pool index 40 is invalid
Bytecode:
...
我试图使用javap
来查找问题,这是指令@29
:
29: invokevirtual #40 // InterfaceMethod java/util/Collection.stream:()Ljava/util/stream/Stream;
以及常量池中的条目(也使用javap
):
使用Eclipse类文件查看器打开类时,@29
的行应为:
Class Format Exception
并且不再显示以下所有说明(除了本地指令,…)。但是,ASM字节码插件编写
INVOKEVIRTUAL java/util/Collection.stream ()Ljava/util/stream/Stream;
在那一行,这似乎是有效的。我做错了什么/错过了什么?我发现了我的错误。错误在于:
invokevirtual #40 // InterfaceMethod
^^^^^^^ ^^^^^^^^^
我在接口上使用invokevirtual方法,这通常不是一个好主意。但是,我认为验证器抛出的错误应该更清楚地说明什么是真正的错误。对于ASM,您将看到此错误,因为有一个不正确的
isInterface
标志。visitMethodInsn
的参数isInterface
指的是目标/所有者/目的地,而不是当前上下文
i、 o.w使用INVOKEVIRTUAL
时,isInterface
为false
有关更多详细信息,请参阅。这可能值得作为编译器错误提交。哦,我看到这是您的编译器,而不是javac。在这种情况下,将错误报告发送给您自己。
invokevirtual #40 // InterfaceMethod
^^^^^^^ ^^^^^^^^^