在jvm加载字节上,带有代码段的java.lang.verifyError。
try{
-----
} catch (NumberFormatException|CalculationException e) {
}
此处的计算exception是自定义异常,它扩展了java.lang.runtimeException,而numberFormateXception是标准Java RuntimeException。当代码编译并运行精细的本地Windows机器时。
它在QA/prod/dev Unix节点之一上使用verifyErr失败,并且在其他Unix节点上正常工作。虽然两个Unix节点具有相同的配置(使用RedHat 6.2和1.8 JDK和相同的版本JAR文件)也比较了Javap -c在两个节点上生成的字节码,并找到了相同的字节。
我找到了在错误节点上解决此问题的两种方法。
1)由于此错误是在字节代码验证步骤出现的,因此通过在Dev Unix框中禁用字节码验证为-xverify:none(也尝试了-xx:-usSplitVerifier,但DINT工作,我认为它是从我认为它禁用的,请尝试使用。JDK 8)但是,由于我们不会在产品中禁用字体上的验证,因此一直在寻找其他解决方法。
2)另一个解决方法是使用父级异常:catch块中的runtimeException而不是组合两个异常。
我无法理解Java是否确实对这种捕捉方式有疑问,为什么编译器DINT抱怨它以及为什么它在一台机器上工作而不是在具有相同配置的另一台机器上工作。此外,错误原因没有意义,上面说:CounculationException(当前帧,堆栈[0])无法分配给'java/lang/runtimeException虽然实际上可以通过
测试的分配if (RuntimeException.class.isAssignableFrom(CalculationException.class)){
System.out.println("Assisgnable");
}
完整的例外详细信息: 位置:
com/markit/valuations/marketdata/snapper/domain/credit/BeanWrapperBuilder_CDXOCompositeVolSurface.getSpreadVol(Lcom/markit/valuations/dates/ImmutableDate;Lcom/markit/valuations/marketdata/data/indexeddata/IndexedData;DLcom/markit/valuations/dates/ImmutableDate;Lcom/markit/valuations/dates/ImmutableDate;Ljava/lang/String;Ljava/lang/String;Lcom/markit/qag/analytics/credit/indexpv/swaption/CreditIndexSwaptionCalculator;Ljava/lang/String;Ljava/lang/String;)Ljava/lang/Double; @51: astore
Reason:
Type 'com/markit/valuations/common/CalculationException' (current frame, stack[0]) is not assignable to 'java/lang/RuntimeException' (stack map, stack[0])
Current Frame:
bci: @0
flags: { }
locals: { 'com/markit/valuations/marketdata/snapper/domain/credit/BeanWrapperBuilder_CDXOCompositeVolSurface', 'com/markit/valuations/dates/ImmutableDate', 'com/markit/valuations/marketdata/data/indexeddata/IndexedData', double, double_2nd, 'com/markit/valuations/dates/ImmutableDate', 'com/markit/valuations/dates/ImmutableDate', 'java/lang/String', 'java/lang/String', 'com/markit/qag/analytics/credit/indexpv/swaption/CreditIndexSwaptionCalculator', 'java/lang/String', 'java/lang/String' }
stack: { 'com/markit/valuations/common/CalculationException' }
Stackmap Frame:
bci: @51
flags: { }
locals: { 'com/markit/valuations/marketdata/snapper/domain/credit/BeanWrapperBuilder_CDXOCompositeVolSurface', 'com/markit/valuations/dates/ImmutableDate', 'com/markit/valuations/marketdata/data/indexeddata/IndexedData', double, double_2nd, 'com/markit/valuations/dates/ImmutableDate', 'com/markit/valuations/dates/ImmutableDate', 'java/lang/String', 'java/lang/String', 'com/markit/qag/analytics/credit/indexpv/swaption/CreditIndexSwaptionCalculator', 'java/lang/String', 'java/lang/String' }
stack: { 'java/lang/RuntimeException' }
Bytecode:
0x0000000: 2c19 0ab9 0015 0200 b800 cb2b 1906 ba00
0x0000010: cc00 00b6 00cd ba00 ce00 00b6 00cf 1909
0x0000020: ba00 d000 00b6 00cf 0eb8 003b b600 d1c0
0x0000030: 0091 b03a 0cbb 0048 59b7 0049 12d3 b600
0x0000040: 4b19 0ab6 004b 12d4 b600 4b2c 1254 b900
0x0000050: 1502 00b6 004b 12d5 b600 4b29 b600 4c12
0x0000060: d6b6 004b 1907 b600 4b12 d7b6 004b 1905
0x0000070: b600 5b12 d8b6 004b 1906 b600 5b12 d9b6
0x0000080: 004b 190b b600 4b12 dab6 004b 1908 b600
0x0000090: 4bb6 004d 3a0d b200 4719 0d19 0cb9 0081
0x00000a0: 0300 0eb8 003b b0
Exception Handler Table:
bci [0, 50] => handler: 51
bci [0, 50] => handler: 51
Stackmap Table:
same_locals_1_stack_item_frame(@51,Object[#535])
原因
当我的依赖项中同一库(JAR)有冲突的版本时,这发生在我身上。更具体地说,我正在导入杰克逊库v2.9.10和v2.11.0的不同版本。
故障排除
以冗长的模式启动应用程序,并使Java日志所有正在加载的类,以查看冲突类的来源。这可以通过传递标志-verbose:class
修复
- 删除依赖关系的冲突版本,并确保所有相关的依赖/库都具有相同的主要版本(至少),最好也是相同的次要版本。
- 删除直接依赖性矛盾版本的依赖性。
- 即使使用
mvn dependency:tree
或Maven Helper插件,您也没有看到任何冲突的依赖项,则相互矛盾的依赖性可能是由库的一个classpath导入的。我知道这听起来很奇怪,因为只有应用程序应该具有classpath,但是如果有人在其库中添加了<addClasspath>true</addClasspath>
,则可能导致此。
依赖关系崩溃是 aditya 指出的原因。如果您使用的是SBT,则可以解决此问题。
首先,将依赖关系图添加到您的全局插件~/.sbt/1.0/plugins/plugins.sbt
:
- SBT 1.4 :添加
addDependencyTreePlugin
- sbt&lt; 1.3:添加
addSbtPlugin("net.virtual-void" % "sbt-dependency-graph" % "0.10.0-RC1")
然后在您的项目运行中
sbt "whatDependsOn com.fasterxml.jackson.core jackson-databind"
是com.fasterxml.jackson.core
是组织,jackson-databind
是库库的工件名称。我的也是因为play-json
使用2.10.4
,并且Contruent软件包使用2.9.9
。您必须根据收到的错误消息找到您的。
然后从这一点开始,您需要就如何解决它做出决定。升级软件包,或降级或排除库。在我的情况下,由于play-json
是从我的应用程序中并不重要的库的传递依赖性,所以我从play-json
库中选择了最简单的路径,并排除了2.10.4
。
您需要在配置中设置以下JVM args:
-xx:-usesplitverifier