比较两个具有不同混淆的.jars

时间:2013-11-01 17:26:47

标签: java comparison byte obfuscation bytecode

我需要比较具有许多相同类但名称不同的jar文件。

假设您正在寻找包含此内容的课程:

public class AStar {
    private int verbose = 0;
    private int maxSteps = -1;
    private int numSearchSteps;
    public ISearchNode bestNodeAfterSearch;

等...但是它被混淆为

public class ard {
    private int fas = 0;
    private int asd = -1;
    private int ags;
    public ars arser;

并且您必须将第一个文件与其他100个文件进行比较才能找到这个文件。 我的猜测是一个字节码比较,但我找不到一个工具或一个方法来比较两个罐子里的所有文件。

5 个答案:

答案 0 :(得分:0)

您应该可以使用ASM启用它。它有很好的文档,还有很多样本。

您根据类型和值构建内部模型,然后比较并吐出相同的类。

如果是你混淆了它,你应该能够获得映射......

答案 1 :(得分:0)

在一般情况下,确定两个任意程序是否对所有输入执行相同的操作是undecidable(可以简化为暂停问题)。

对于以下内容,我假设混淆不会破坏类结构:它只会重命名字段,方法和类,并可能混淆字节码。

假设您正在寻找一个等同于某个类C的混淆类。以下是您可以执行的一些搜索,按难度递增顺序:

  1. 查找与C具有完全相同数量的字段和方法的所有类。
  2. 对于每个混淆的类,计算它包含的字段类型集(但是,为简单起见,不要包含指向其他混淆类的类型)。这组字段类型不是C字段类型的子集的所有类都可以过滤掉。
  3. 对方法签名执行相同的操作。
  4. 你可以走得更远,但可能会变得非常复杂。
  5. 最后,最有效的方法取决于混淆器所做的具体事情,而不是试图隐藏。

    ASM是一个用于解析和处理.class文件的好库。

答案 2 :(得分:0)

如果模糊处理仅更改 变量名,而不是变量顺序或任何编译器生成的字节码,则应该能够使用ASM或Javassist或其他字节码库执行此操作。实际上,下面的列表可以使用常规的Java反射来完成。

如果符合以下条件,两个类文件将成为平等的候选者:

  1. 他们拥有相同数量的方法
  2. A类和B类方法的参数签名之间存在1对1的映射
  3. 匹配方法也匹配标志(私有/公共,静态,抽象等)
  4. 这将是一个非常好的匹配。除此之外,您可能需要了解字节代码的详细信息。字节代码应该类似,但对Const Pool的引用可能会被扰乱。你必须破译那些。例如,一个类可能ldc #12而另一个类可能ldc #34;如果事实证明A类中的#12与B类中的#34相同,则它们匹配(至少为此)。

    如果混淆器重新编写私有方法的参数顺序,则很难轻易检测到匹配。不过,也许您需要做的就是将其缩小到合理数量的候选人,因此将上述列表应用于公共和受保护的方法可能就是您所需要的。

答案 3 :(得分:0)

我使用Beyond Compare来比较jar文件:

http://www.scootersoftware.com/

使用其他文件格式比较.class文件(反编译)

可能会有运气

http://www.scootersoftware.com/download.php?zz=kb_moreformats_win

答案 4 :(得分:0)

我过去做过这个,但问题是通常还需要大量的手工工作来确定保留的信息类型,以及与之比较的库。

例如,在一个案例中,我发现混淆的Jar已经向库类中添加了一个方法,该方法抛弃了比较,直到找到并解释它为止。另一个常见问题是混淆器将删除未使用的方法和接口,有时会添加特定于混淆器的方法。

为了获得好的结果,您不能只考虑个别课程。您需要匹配类之间的继承层次结构,接口和交叉引用,以便明确地匹配大多数类,即使这样,它也不总是成功。

幸运的是,他们几乎从不重新排序或更改字段和方法的签名。否则,收集足够的信息以明确地匹配类是非常困难的。实际上,通常有类具有完全相同的方法和继承(例如,两个实现相同接口的类)。如果你很幸运,你将能够通过匹配第三类的引用来推断它,但这并不总是可行。

无论如何,如果你愿意,我可以发给你我的代码。它专为识别混淆应用程序中包含的开源库而设计,但它也可能适用于匹配两个混淆的应用程序。