确定.class文件是否使用调试信息编译?

时间:2009-10-02 08:00:25

标签: java class debugging

如果使用调试信息编译的话,我如何确定任何Java .class文件?

如何准确判断使用了-g {source | lines | vars}选项?

3 个答案:

答案 0 :(得分:43)

如果你在命令行上,那么javap -l将显示LineNumberTable和LocalVariableTable(如果存在):

peregrino:$ javac -d bin -g:none src/Relation.java 
peregrino:$ javap -classpath bin -l Relation 
public class Relation extends java.lang.Object{
public Relation();

peregrino:$ javac -d bin -g:lines src/Relation.java 
peregrino:$ javap -classpath bin -l Relation 
public class Relation extends java.lang.Object{
public Relation();
  LineNumberTable: 
   line 1: 0
   line 33: 4

peregrino:$ javac -d bin -g:vars src/Relation.java 
peregrino:$ javap -classpath bin -l Relation 
public class Relation extends java.lang.Object{
public Relation();

  LocalVariableTable: 
   Start  Length  Slot  Name   Signature
   0      5      0    this       LRelation;
如果出现在反编译的开头,

javap -c将显示源文件:

peregrino:$ javac -d bin -g:none src/Relation.java 
peregrino:$ javap -classpath bin -l -c Relation | head
public class Relation extends java.lang.Object{
  ...

peregrino:$ javac -d bin -g:source src/Relation.java 
peregrino:$ javap -classpath bin -l -c Relation | head
Compiled from "Relation.java"
public class Relation extends java.lang.Object{
  ...

以编程方式,我会查看ASM,而不是编写另一个字节码阅读器。

答案 1 :(得分:2)

您必须检查类文件中的Code structure并查找LineNumberTableLocalVariableTable属性。

ASM或Apache Commons BCEL(字节代码工程库)等工具将有助于:https://commons.apache.org/proper/commons-bcel/apidocs/index.html?org/apache/bcel/classfile/LineNumberTable.html

答案 2 :(得分:0)

基于以上两个答案(Aaron Digulla和Pete Kirkham),您可以直接使用javap -v检查jarfile或classfile。我发现这比使用类路径要简单一些。 jarfile大小写时,!需使用单引号。

javap -v 'jar:file:///Absolute/Path/To/JarFile.jar!/package/name/using/slashes/ClassName.class' | grep "\(Compiled from\|LineNumberTable\|LocalVariableTable\)" | head

或(不需要绝对路径来检查类文件)

javap -v Path/To/ClassName.class | grep "\(Compiled from\|LineNumberTable\|LocalVariableTable\)" | head

如果结果不清楚或格式更改,请用管道输送到less而不是grep,然后进行查看。