jvm *** java.lang.instrument声明失败 *** 的含义/原因是什么:“!errorOutstanding”消息转换方法调用失败?

kuhbmx9i  于 2022-11-07  发布在  Java
关注(0)|答案(4)|浏览(266)

当我使用gradle运行测试时,我开始在控制台上得到下面的输出。这个输出来自JVM,而不是我的代码。KotlinDSL用于配置我的gradle版本。


***java.lang.instrument ASSERTION FAILED***: "!errorOutstanding" with message transform method call failed at  line: 873
***java.lang.instrument ASSERTION FAILED***: "!errorOutstanding" with message transform method call failed at  line: 873
***java.lang.instrument ASSERTION FAILED***: "!errorOutstanding" with message transform method call failed at  line: 873
***java.lang.instrument ASSERTION FAILED***: "!errorOutstanding" with message transform method call failed at  line: 873

这是Java 11上发生的事情

java --version
openjdk 11.0.6 2020-01-14
OpenJDK Runtime Environment AdoptOpenJDK (build 11.0.6+10)
OpenJDK 64-Bit Server VM AdoptOpenJDK (build 11.0.6+10, mixed mode)

这个输出不是来自我的代码,它似乎来自JVM。没有列出文件名,以前版本的Java似乎有一个与此https://bugs.openjdk.java.net/browse/JDK-8061621相关的错误
JPLISAgent.c的第873行可能是生成消息的内容。

  • 更新日期:*

我检查了我所有的CI日志来确定导致这个问题的提交。在一个基于Jackson的Json格式化程序实用程序的单元测试中跟踪到了这个代码。

// try with a circular dependencies
    Node a = new Node("a");
    Node b = new Node("b");
    a.setChild(b);
    b.setParent(a);

    assertThatExceptionOfType(JsonUtilsException.class).isThrownBy(() -> JsonUtils.toJson(a));

特别是循环依赖触发了JVM输出,我猜Jackson真的被循环依赖绊倒了,但我不明白为什么会导致JVMAssert错误。
问题:-此警告/错误的含义是什么?-此错误的典型原因是什么,JVM中的Assert失败?

ni65a41a

ni65a41a1#

该消息确实来自JPLISAgent.c:873。
这意味着您的JVM有一个实现java.lang.instrument.ClassFileTransformer的代理,并且方法transform(java.lang.Module, java.lang.ClassLoader, java.lang.String, java.lang.Class<?>, java.security.ProtectionDomain, byte[])抛出了异常。
在我的例子中,我同时使用了BlockHound和ByteBuddy(由BlockHound加载)。代码中的StackOverflowError触发了新类的加载,然后两个代理都抛出了StackOverflowError,但没有捕获它。我创建了an issue for ByteBuddy,但我开始认为只有JDK中的错误报告需要更改。
由于异常的源代码是Java代码,因此您可以附加一个调试器,并在抛出的StackOverflowError上设置一个断点。您很有可能首先在您的代码或Jackson中发现StackOverflowError,您应该修复/报告它。

w6lpcovy

w6lpcovy2#

您的测试正在生成非常大的异常原因链。
下面是一些Scala代码,它们生成一个很长的异常原因链,然后抛出它:

val iter = Iterator.from(0).map(_.toString).map(new Exception(_))
val es = iter.take(1024 * 1024).toSeq
for {
  (e0, e1) <- es.zip(es.tail)
} {
  e0.initCause(e1)
}
//es.last.initCause(es.head) //uncomment this line for extra fun
throw es.head

这会产生相同的


***java.lang.instrument ASSERTION FAILED***: "!errorOutstanding" with message transform method call failed at JPLISAgent.c line: 844
qncylg1j

qncylg1j3#

我在进行递归调用时得到了这个(在没有意识到的情况下)此外,此调用有一个try/catch,我在其中捕获了Throwable(可能的最高异常类型)。我的解释是我的catch捕获了StackOverflowException(并进一步对此进行了工作),这让整个事情变得疯狂!当我在IntelliJ调试器中运行它时,我不能真正停止线程-不知怎么的,新的线程正在生成。一旦我删除递归调用,一切都很好。

cunj1qz1

cunj1qz14#

当我用spring验证循环依赖时也会出现这个问题,我的代码应该是JVM中报告的错误,检查你的代码,一定有死循环。

相关问题