如何从已编译的Java类/ jar文件中删除方法?

时间:2016-09-19 18:03:55

标签: java reflection bytecode javassist

我有一个JAR文件并且有一个静态类,我无法反编译它,它搞砸了。其中有一种方法可以返回一个不存在的类。不知道如何,但我得到了NoClassDefFoundError。即使我没有使用该方法,它仍然会崩溃。所以我需要以某种方式删除它,它应该工作正常。我知道可以使用Reflection或Javassist,但不知道如何。

请注意,生产版本显然,只是一些白帽黑客。

2 个答案:

答案 0 :(得分:2)

我认为你错了:如果永远不会调用那个方法,那么JVM 很可能不会尝试加载该类。

你看,类加载的重点 - 发生 lazy ;当你加载类X,并且X需要Y,Z ...时,只有在执行需要Y,Z加载的代码时才加载Y和Z.

换句话说:NoClassDefFound错误实际上告诉您某些东西(可能是JAR中的某个静态init)正在调用该方法。

因此,解决方案不是"切断"那个方法(这会导致另一个异常,比如MethodNotFound!)。相反,您应该尝试创建一个虚拟类,以便根本不会遇到该异常。或者:您的JAR至少缺少一个依赖项。您可以尝试解决这种依赖关系 - 也许您可以在某个地方找到该课程,或者您可以“#34; build"你自己的版本(第二个想法可能很难来纠正)。

答案 1 :(得分:1)

GhostCat已经解释了为什么你的问题没有删除方法。但我想我应该回答原来的问题,以防其他人想知道。

从类文件中删除方法的最佳方法是使用Krakatau对其进行反汇编,从.j文件中删除所需的方法,然后重新组合它。这个方法允许你编辑任何类文件,无论多么奇怪。 (如果您发现Krakatau反汇编程序无法处理的任何有效类文件,请提交错误)。

反汇编时,您可能还想传递-roundtrip选项。这不是正确性所必需的,但它可以防止重新排列常量池,从而减少生成的类文件的二进制差异。另一方面,-roundtrip也使得在.j文件中找到所需方法变得更加困难。

相关问题