`

javap

    博客分类:
  • JAVA
阅读更多

 javap,是JDK自带的反汇编工具,用于将Java字节码文件反汇编为Java源代码

也许我们很少会使用到javap工具,因为现在有很多好的反编译工具,但是我在此介绍这个工具不是使用它进行反编译,而是查看java编译器为我们生成 的字节码,通过比较字节码和源代码,我们可以发现很多的问题,一个很重要的作用就是了解很多编译器内部的工作机制,在笔者以前的几篇文章中就是借助此工具 的,本站有这些文章的原文《深入剖析java类的构造方式》和《使用String还是StringBuffer》。
 下面我们通过具体的一个例子来简单的讲讲这个工具的作用,你不需要很深入的使用,这个简单的介绍和简单的使用就可以使你受益非浅。
 源代码:

Java代码  收藏代码
  1. class StringTest   
  2. {  
  3.     public static void main(String[] args)   
  4.     {  
  5.         String result="";  
  6.         result+="ok";  
  7.     }  
  8. }  

 在反编译前你当然需要先编译这个类了:javac -g StringTest.java(使用-g参数是因为要得到下面javap -l时的输出需要使用此选项)
编译完成后,我们在使用不同的选项看看不同的效果:
1、先看看最简单的不带参数的情况:javap StringTest:

Java代码  收藏代码
  1. Compiled from StringTest.java  
  2. class StringTest extends java.lang.Object {  
  3.     StringTest();  
  4.     public static void main(java.lang.String[]);  
  5. }  

 不带参数的情况将答应类的public信息,包括成员和方法
从上面的输出中我们确定了两个知识:如果类没有显示的从其它类派生那么它就是从Object派生;如果没有为类显示的申明构造方法,那么编译器将为之生成一个缺省构造方法(不带参数的构造方法)

2、javap -c StringTest:

输出 写道
Compiled from StringTest.java
class StringTest extends java.lang.Object {
StringTest();
public static void main(java.lang.String[]);
}

Method StringTest()
   0 aload_0
   1 invokespecial #1 <Method java.lang.Object()>
   4 return

Method void main(java.lang.String[])
   0 ldc #2 <String "">
   2 astore_1
   3 new #3 <Class java.lang.StringBuffer>
   6 dup
   7 invokespecial #4 <Method java.lang.StringBuffer()>
  10 aload_1
  11 invokevirtual #5 <Method java.lang.StringBuffer append(java.lang.String)>
  14 ldc #6 <String "ok">
  16 invokevirtual #5 <Method java.lang.StringBuffer append(java.lang.String)>
  19 invokevirtual #7 <Method java.lang.String toString()>
  22 astore_1
  23 return

 带-p参数将额外的打印字节码信息
前面的和不带参数的输出一样,后面的显示了方法的具体的字节码,从这个输出里面我们又可以了解更多的内容,首先 是编译器生成的的缺省构造方法的内容为调用父类的构造方法super()(需要说明的是使用DJ反编译的源代码中这个缺省构造方法没有这个调用,这可能是 该反编译器的一种优化),main()方法的字节码信息的内容可以参考《使用String还是StringBuffer》一文的叙述。

 

3、javap -l StringTest :

输出 写道
Compiled from StringTest.java
class StringTest extends java.lang.Object {
StringTest();
public static void main(java.lang.String[]);
}

Line numbers for method StringTest()
line 1: 0

Local variables for method StringTest()
StringTest this pc=0, length=5, slot=0

Line numbers for method void main(java.lang.String[])
line 5: 0
line 6: 3
line 7: 23

Local variables for method void main(java.lang.String[])
java.lang.String[] args pc=0, length=24, slot=0
java.lang.String result pc=3, length=20, slot=1

-l参数将显示行号和局部变量表

从上面的输出中我们可以得到方法中的变量和方法的源代码对于字节码信息的,例如对应main()方法,它的变量为输入参数args以及局部变量 result,方法的源代码的第5行对应字节码的第0个偏移量,第5行对应字节码的第3个偏移量,而第7行对应字节码的第23偏移量(参看 javap -c的输出前面的偏移量),第7行实际是没有语句的,但是有一个隐含的return,而偏移量23实际对应的也是return调用

4、javap -p StringTest:

输出 写道
Compiled from StringTest.java
class StringTest extends java.lang.Object {
StringTest();
public static void main(java.lang.String[]);
}

 -p参数将额外的打印private成员和方法的信息,因为这个类没有因此输出相同

这几个参数几乎就可以构成javap的最常使用的集合,最常用的应该还是-c选项,因为可以打印字节码的信息,关于这些字节码的详细涵义在Java 虚拟机规范中定义,感兴趣的可以查看相关的信息!

 

备上使用指南:

用法: javap <options> <classes>
可能的选项包括:
  -help  --help  -?        打印用法信息
  -version                 版本信息
  -v  -verbose             打印附加信息
  -l                       打印行号和本地变量表
  -public                  仅显示public类和成员
  -protected               显示protected/public类和成员
  -package                 显示package/protected/public类和成员(默认值)
  -p  -private             显示所有的类和成员
  -c                       反汇编代码
  -s                       打印内部类型签名
  -sysinfo                 显示将被处理的类的系统信息(路径,大小,日期,MD5 哈希值)
  -constants               显示static final常量
  -classpath <path>        指定查找用户类文件的位置
  -bootclasspath <path>    覆盖由引导类加载器所加载的类文件的位置

我们通常以如下形式使用javap:

1、不带任何可选参数(如果字节码文件就位于当前工作目录,可以不写类的包名):

#实际上等同于javap -package Person
javap Person

2、反汇编指定目录下的字节码文件:

javap -classpath D:/java/lib cn.softown.Person

3、反汇编字节码文件为JVM可以识别、执行的字节码命令:

javap -c Person

以下是可选参数的详细说明:

-classpath <pathlist>
手动指定用户class字节码文件的存放目录,javap程序将在此目录下查找class文件,多个路径以英文分号分隔。例如:javap -classpath D:\java\test Person(即使DOS窗口的当前工作目录为其他任意路径,该命令均可正确执行)。
-s
打印变量的内部类型签名,例如:javap -classpath D:\java\test -s Person
-extdirs <dirs>
指定javap搜索已安装的java扩展的位置,默认的java扩展的位置为jre\lib\ext。例如:javap -classpath D:\java\test -extdirs D:\java\myext Person
-bootclasspath <pathlist>
指定使用Java底层类加载器(bootstrap class loader)加载的字节码文件的位置。例如:javap -classpath D:\java\test -bootclasspath D:\java\core Person
-verbose
打印方法参数和本地变量的数量以及栈区大小。
-J<flag>
传递运行时标识参数给javap,例如javap -J-version,可以有多个命令,中间以空格隔开。

参考文章:

http://www.javaresearch.org/article/768.htm .

http://chenhua-1984.iteye.com/blog/423389

软件指南针(http://www.softown.cn)

分享到:
评论

相关推荐

    javap使用(1).docx

    ### javap 使用详解 #### 一、概述 `javap` 是 Java 开发工具包 (JDK) 中的一个重要工具,主要用于反编译 `.class` 文件中的字节码。通过 `javap`,开发者能够深入了解 Java 编译器是如何处理源代码并生成字节码的...

    Java运行原理 javap命令运行结果

    ### Java运行原理与javap命令运行结果解析 #### 一、Java运行原理概述 Java是一种广泛使用的编程语言,它的程序可以在任何支持Java虚拟机(JVM)的操作系统上运行,而无需重新编译。Java程序的执行过程可以分为...

    javap写的完整记事本

    【标题】"javap写的完整记事本"是一款利用Java编程语言实现的文本编辑器,它具有基础的记事本功能,并且增加了字体格式和字体颜色的设定,为用户提供更为丰富的文本编辑体验。这款记事本应用充分利用了Java的Swing库...

    HelloWorld的javap -verbose HelloWorld 字节码初探

    标题中的“HelloWorld的javap -verbose HelloWorld”指的是在Java编程环境中,通过`javap`这个命令行工具来反汇编一个简单的“HelloWorld”程序,以深入理解字节码的工作原理。`javap`是Java Platform Debugger ...

    javap2p技术内幕.part2.rar

    javap2p 技术内幕javap2p 技术内幕javap2p 技术内幕javap2p 技术内幕

    javap使用说明文档

    javap 使用说明文档 javap 是 JDK 中的一个命令行工具,主要用于对给定的 class 文件进行反编译,了解 Java 编译器内部的工作机制,并提高程序执行的效率。下面是 javap 的使用说明。 1. javap 的基本用法 javap ...

    ndk开发实战javap签名篇

    标题“ndk开发实战javap签名篇”指向了一个针对使用NDK进行Android应用开发过程中的具体技术实践——使用javap命令来获取Java类的签名信息,并生成相应的C/C++头文件,这对于在C/C++代码中调用Java层的方法是必需的...

    JavaP2P技术内幕 part3

    标题:"JavaP2P技术内幕 part3" 描述:"JavaP2P技术内幕太大不能上传,分5部分传递" 从标题和描述中,我们可以提炼出的关键知识点主要围绕JavaP2P技术,即Java对等网络(Peer-to-Peer Network)技术。P2P技术在...

    JavaP2P技术内幕 part4

    标题:"JavaP2P技术内幕 part4" 描述:"JavaP2P技术内幕太大不能上传,分5部分传递" 从标题和描述中,我们可以提炼出的关键知识点主要围绕JavaP2P技术,即Java对等网络(Peer-to-Peer Network)技术。在IT行业中,...

    javaP2P总结

    Java P2P(对等网络)技术是一种分布式通信模型,其中每个节点既是客户端也是服务器,可以互相分享资源和服务。在Java中实现P2P技术,需要深入理解网络编程、多线程、数据传输协议等核心概念。下面我们将详细探讨...

    使用类分解器Javap分析Java字节码

    `Javap`是Java开发工具包(JDK)中自带的一个命令行工具,专门用于分析Java字节码,帮助开发者理解类文件的内部结构。在这个话题中,我们将深入探讨如何使用`Javap`作为类分解器来解析和理解Java字节码。 首先,让...

    wtl_wtl-implementation_of_javap-master_C++_

    标题 "wtl_wtl-implementation_of_javap-master_C++_" 暗示这是一个C++项目,其目标是实现Java的`javap`工具的功能。`javap`是Java开发工具包(JDK)的一部分,它用于反汇编Java字节码,帮助开发者查看和理解类文件...

    Java的class文件结构介绍以及如何实现javap

    NULL 博文链接:https://bolinyang.iteye.com/blog/1830472

    javap2p基于jxta

    标题“javap2p基于jxta”表明这个压缩包文件包含了一个使用JXTA库实现的Java P2P示例项目。这个项目可能是为了帮助开发者理解和学习如何利用JXTA进行P2P通信。通过分析和运行“myjxtademo”这个示例,我们可以深入...

    javap写的一个动态日历

    【标题】:“javap写的一个动态日历” 这个标题表明我们正在讨论一个使用Java编程语言编写的日历程序。`javap`在这里可能被误用,实际上`javap`是Java平台的标准工具,用于反汇编Java类文件,展示字节码和相关的元...

    javap命令的使用技巧

    Java 中 javap 命令的使用技巧 javap 命令是 JDK 自带的一个工具,它可以对代码反编译,也可以查看 Java 编译器生成的字节码,对代码的执行过程进行分析,了解 JVM 内部的工作。javap 命令可以将 class 文件反编译...

    JavaP7架构师课程 JavaP7架构师课程

    JavaP7架构师课程

    JavaP2P技术内幕 part5

    根据提供的标题“JavaP2P技术内幕 part5”和描述“JavaP2P技术内幕太大不能上传,分5部分传递”,我们可以推断出这是一系列关于Java P2P(Peer-to-Peer)技术的深入讲解文档的一部分。由于提供的具体内容部分没有...

    javap2p聊天工具源码

    在“javap2p聊天工具源码”中,我们可以深入理解以下几个关键知识点: 1. **Java编程语言**:Java是用于开发此聊天工具的基础,它是一种跨平台、面向对象的编程语言,具有丰富的类库和强大的性能,适合构建复杂的...

    javap---application--键盘钢琴

    标题“javap---application--键盘钢琴”所指的是一款用Java编程语言开发的应用程序,它模拟了一款键盘钢琴。在Java编程中,"Application"通常指的是具有图形用户界面(GUI)的桌面应用程序,而非Web应用或移动应用。...

Global site tag (gtag.js) - Google Analytics