“检测”;超级";使用字节码的java代码中的word
我目前正在尝试计算java程序中超级调用的数量。换句话说,我想计算给定代码中“super”的数量。我曾尝试使用操作码中的invokespecial方法,但问题是它会计算“super”一词出现的其他情况“检测”;超级";使用字节码的java代码中的word,java,bytecode,super,Java,Bytecode,Super,我目前正在尝试计算java程序中超级调用的数量。换句话说,我想计算给定代码中“super”的数量。我曾尝试使用操作码中的invokespecial方法,但问题是它会计算“super”一词出现的其他情况 他不在场 我将非常感谢任何帮助,这个问题一直是一个巨大的痛苦 //编辑 我想数一数“超级”这个词;callssuper是一个关键字,表示任何父类 您不需要super()调用计数,因为每个构造函数将有一个调用计数(除了java.lang.Object) 为了确保使用了super,您必须查看使用thi
他不在场 我将非常感谢任何帮助,这个问题一直是一个巨大的痛苦 //编辑
我想数一数“超级”这个词;calls
super
是一个关键字,表示任何父类
您不需要super()
调用计数,因为每个构造函数将有一个调用计数(除了java.lang.Object
)
为了确保使用了super
,您必须查看使用this
作为父类上非静态方法的第一个参数的方法
您可以执行类似于对父类字段的访问计数的操作。
super
严格来说是Java语言级别的标识符;字节码中没有直接等价物
要查找调用站点,如super.method()
,可以查找满足以下条件的invokespecial
指令:
)OuterClass.this.privateMethod()
时出现的误报一样。在这种情况下,编译器将发出一个静态访问器方法,该方法使用invokespecial
在OuterClass
实例上调用privateMethod()
如果要包含super()
构造函数调用,则需要在调用另一个构造函数的构造函数中查找invokespecial
指令;通过比较被调用构造函数的声明类型与当前类型,可以筛选出this()
调用
您无法可靠地确定原始源中何时显式使用了super.field
,因为在许多情况下(甚至是非限定访问),它在语义上等同于this.field
。如果要包括任何超类字段访问,只需将字段的声明类型与任何getfield
和putfield
指令的当前类型进行比较即可。否则,您所能做的就是确定必须使用super.field
的位置,即目标字段被当前类中同名字段隐藏的任何字段访问
如果您想检测形式为OuterClass.super.privateMethod()
的访问,那么您会遇到一些麻烦。编译器为这些方法生成静态访问器方法,而约定是编译器的一个实现细节,因此可靠地识别它们是非常重要的。您还必须分析生成的方法,以验证调用的方法的声明类型与实例参数类型不匹配(假设编译器实际将参数键入为OuterClass
,而不是直接替换其超类)。如果代码被混淆了,那就忘了它。不能只解析.java
文件吗?的确,这是一个选项,但我更喜欢字节码解决方案。如果我使用解析器,我还必须计算我想要避免的构造函数!尤克萨里斯托·潘托斯:-)谢谢彼得,我更新了问题。我想数一数所有的超级。有些东西不仅仅是超级呼叫。有什么区别?正如我所说,您不需要构造函数调用。invokespecial还用于调用私有方法。哦,您说得对!这会使事情变得棘手。将更新。更新以解决invokespecial
以及OuterClass.super
引用的其他边缘情况。另外,考虑到后者,我发现我的反编译器中有一个bug\o/