继续跟着上一次【https://www.cnblogs.com/webor2006/p/9502507.html】的那10个代表code的字节分析,如下:

而这些字节其实对应的信息是它:

所以问题就来了,aload_0不是助记符信息么,怎么就能够跟字节码文件中的字节对应上呢?所谓助记符其实也就是帮忙我们去记忆的符合,在底层其实也是对应的一个个十六进制的数字的,其它aload_0对应的就是2A这个十六进制数字,凭什么这么说?因为有jclasslib这么好的工具能帮我们对应上,将鼠标放在助记符上发现是一个可以点的链接,如下:

点一下“aload_0”发现居然链到了oracle的官网上的说明上去了,如下:

所以第一个字节已经分析完了,确实是跟助记符对应上了,接着来分析第二个字节:

而在jsclasslib中对应的第二个助记符是“invokespecial”,点击链到官网看一下:

而它的作用可以理解成就是调用父类的方法,很明显对于咱们自定义的子类肯定会去调用父类的构造方法,而这个助记符是有参数的:

其实也就是往后的两个字节就是该助记符所对应的参数,如下:

对应常量池为:

也就是构造方法嘛,如jsclasslib所示:

接下来继续往下走一个字节:

又对应aload_0,如下:

接着再往后看一个字节:

其实它就是对应下一个助记符,如下:

为啥如此任性呢,因为点击查看一下说明就晓了啦:

为啥要push一个1呢?实际就是给咱们定义的成员变量a赋值,如下:

可见,该变量的赋值是在默认构造函数中进行的,而不是直接进行赋值的,这也就是分析字节码文件的好处,可以更加真实的发现底层细节。

接下来再数一个字节:

当然它又对应另一个助记符喽,如下:

点击看一下官网说明:

接下来该助记符是携带有参数的,所以再往后数两个字节:

对应常量池:

也就是给MyTest1的成员变量a赋值为1。

接下来再数一个字节:

对应于如下助记符:

点击确认一下:

至此整个构造方法就已经执行完了。发现通过分析字节码也能获得不少新知识嘛,仅通过这个构造函数的执行流程就能知道了对于我们定义的成员变量原来是在构造方法中进行赋值而非直接赋值的,还是挺有价值的。

好,方法的code分析完之后,则就得往下进行分析了,先来查看一下结构类型:

也就是再数两个字节,看一下:

说明该方法木有异常信息,所以接下来的异常表就不会显示在字节文件当中了:

其中关于异常还需解释一下:

  • exception_table,这里存放的是处理异常的信息。
  • 每个exception_table表项由start_pc、end_pc、handler_pc、catch_type组成。
  • start_pc和end_pc表示在code数组中的从start_pc到end_pc处(包含start_pc,不包含end_pc)的指令抛出的异常会由这个表项来处理。
  • handler_pc表示处理异常的代码的开始处。catch_type表示会处理的异常类型,它指向常量池里的一个异常类。当catch_type为0时,表示处理所有的异常。

接下来就到属性相关的东东了,如下:

所以往下数2个字节:

说明该方法有两个属性,往下数两个字节则是第一个属性的名字索引,如下:

也就是对应第10的常量池,为:

该属性用来表示code数组中的字节码和Java代码行数之间的关系。这个属性可以用来在调试的时候定位代码执行的行数。而该属性的结构为:

其中attribute_name_index就是常量索引10,接下来数4个字节则是属性的长度attribute_length,如下:

也就是属性的长度为10,也就是接下来10个字节则为LineNumberTable的属性信息,如下:

看一下jclasslib:

下面具体来分析一下这10个字节,根据结构体来看:

先2个字节表示属性表有几对映射,如下:

说明有两对映射,然后再回到结构体中,每对映射的内容为:

每对占4个字节,先看第一对映射:

也就是start_pc=0;line_number=3,对应于jclasslib:

由于咱们源代码木有构造方法,所以字节码对应源代码就在第3行,如下:

接下来看第二对映射:

也就是start_pc=4;line_number=4,对应于jclasslib:

因为成员变量的赋值是在构造方法中完成的,所以对应第4行代码:

好,方法的第一个属性已经完了,接下来以同样的顺序来查看方法的第二个属性信息了,走2个字节来看属性名称索引,如下:

对应第11个常量池索引,如下:

它的结构跟LineNumberTable差不多的,往后数四个字节则是局部变量表所占的长度:

长度为12,如jclasslib所示:

然后往后数12个字节则是局部变量的具体信息,首先两个字节则为局部变量的个数,如下:

呃~~构造方法哪来的局部变量呢,好奇怪,先不管先来把其它字节分析完,再往后四个字节表示start_pc和length,如下:

如jclasslib所示:

接下来则为局部变量的索引为0,也就是第一个局部变量:

再往后两个字节则是局部变量对应常量池的索引,如下:

再接下来两个字节则是对该局部变量的一个描述常量索引,如下:

所以对应jclasslib中可以看到:

那思考一下为啥在构造方法中会有一个this的局部变量呢?我们知道在所有方法中我们都能使用this关键字来访问当前的对象,而从字节层面来讲其实this是作为方法的第一个参数传进来的,也就是说对于Java的一个实例方法而言最少会有一个this的局部变量存在!

还剩最后两个字节则为stackmaptable信息,JDK1.6加入的,主要做校验检查的,因为0嘛所以后面肯定木有相关的信息了,这里就直接忽略,如下:

Java字节码方法表与属性表详解的更多相关文章

  1. Java字节码(.class文件)格式详解(一)

    原文链接:http://www.blogjava.net/DLevin/archive/2011/09/05/358033.html 小介:去年在读<深入解析JVM>的时候写的,记得当时还 ...

  2. Java线程通讯方法之wait()、nofity() 详解

    Java线程通讯方法之wait().nofity() 详解 本文将探讨以下问题: synchronized 代码块使用 notify()与notifyAll()的区别 Java wait(),noti ...

  3. JVM Java字节码方法表与属性

    方法表 1.methods_count  method_info,前三个字段和field_info一样 2.方法的属性结构 方法中的每个属性都是一个attribut_info结构 JVM定义了部分at ...

  4. Java字节码方法表与属性表深度剖析

    方法表: 在上一次咱们已经分析到了字段信息了,如下: 紧接着就是方法相关的信息了: 而它展开之后的结构为: 所以往后数2个字节,看一下方法的总数: 3个方法,可咱们只定义了两个方法呀: 因为编译器会为 ...

  5. Java字节码方法表结构深度剖析

    继续上一次[https://www.cnblogs.com/webor2006/p/9459681.html]的字节码分析,这次来分析一下最为复杂的方法表的信息,如下: 而上一次分析到了属性表的位置在 ...

  6. Java线程阻塞方法sleep()和wait()精炼详解

    版权声明:因为个人水平有限,文章中可能会出现错误,如果你觉得有描述不当.代码错误等内容或者有更好的实现方式,欢迎在评论区告诉我,即刻回复!最后,欢迎关注博主!谢谢 https://blog.csdn. ...

  7. Java字节码操纵框架ASM小试

    本文主要内容: ASM是什么 JVM指令 Java字节码文件 ASM编程模型 ASM示例 参考资料汇总 JVM详细指令 ASM是什么 ASM是一个Java字节码操纵框架,它能被用来动态生成类或者增强既 ...

  8. 从 HelloWorld 看 Java 字节码文件结构

    很多时候,我们都是从代码层面去学习如何编程,却很少去看看一个个 Java 代码背后到底是什么.今天就让我们从一个最简单的 Hello World 开始看一看 Java 的类文件结构. 在开始之前,我们 ...

  9. 空手套白狼,硬阅java字节码class文件

    如下,是一些java字节码也就是原始的class文件,当应用部署到线上之后,我们能够看到的也就是这样的字样了.那么怎样解呢?就让我们一起,来解读解读字节码吧! Offset A B C D E F C ...

随机推荐

  1. 共享文件word / excel /ppt 被用戶自己锁定无法编辑-解決方法

    共享文件word / excel /ppt 被用戶自己鎖定無法編輯,但用戶嘗試過關閉所有文件和重啓過系統,依然無法編輯. 搜到解決方法: Just in case someone looking fo ...

  2. 【计算机视觉】Selective Search for Object Recognition论文阅读2

    Selective Search for Object Recognition 是J.R.R. Uijlings发表在2012 IJCV上的一篇文章.主要介绍了选择性搜索(Selective Sear ...

  3. Python 面向对象总结

    面向对象 类 class 类型 类变量 实例方法 init attack bite 类指针 - 指向父类 对象 对象指针 实例变量 self.name slef.age 组合 一个对象作为一个属性 s ...

  4. for i in range()

    for i in range()就是python中的循环语句 有以下三种常见用法: 1.range(3) [0,3)即0,1,2 2.range(1,3) [1,3)即1,2 3.range(1,5, ...

  5. [转帖][思路/技术]Mimikatz的多种攻击方式以及防御方式

    [思路/技术]Mimikatz的多种攻击方式以及防御方式 https://bbs.ichunqiu.com/thread-53954-1-1.html 之前学习过 抄密码 没想到还有这么多功能.   ...

  6. [转帖]AIDA64 6.10版发布:全面支持中国兆芯、海光x86 CPU

    AIDA64 6.10版发布:全面支持中国兆芯.海光x86 CPU https://www.cnbeta.com/articles/soft/892877.htm 支持国产x86了 作为硬件识别工具领 ...

  7. (九)Javabean与Jsp(来自那些年的笔记)

    目录 JavaBean 在JSP中使用JavaBean 标签用法 带标签体的 JavaBean 标签 setProperty 标签 getProperty 标签 JSP开发模式 案列:使用 模式一 编 ...

  8. 华为S5700系列交换机配置文件导出、导入

    一.导出 配置用户名密码,使能ftp ftp server enable aaa local-user putty password cipher putty123 local-user putty ...

  9. 基于聚类K-Means方法实现图像分割

    ”“”K-Means to realize Image segmentation “”“ import numpy as np import PIL.Image as image from sklea ...

  10. java. util. concurrent. atomic

    一.原子更新基本类型 AtomicInteger AtomicBoolean AtomicLong 二.原子更新数组 AtomicIntegerArray AtomicLongArray Atomic ...