字节码文件

  • 查看字节码工具:Idea插件(jclasslib)
  • 一堆十六进制数,JVM以两个十六进制值为一组,一个十六进制数表示4位(0000),8位等于一个字节,即以字节为单位进行读取

image.png

  • 字节码文件由十部分按固定顺序组成

image.png
魔数 版本号 常量池 访问标志 当前类在常量池中的索引 父类在常量池中的索引 接口在常量池中的索引 字段表 方法表 附加属性

  1. 魔数:0xCAFEBABE

  2. 版本号:次版本号+主版本号 各2个字节

  3. 常量池:常量池计数器+常量池数据区

    • 计数器:用两个字节来表示常量池大小
      复制代码
    • 数据区:  
        1. 字面量(final修饰的常量值和八种基本数据类型:byte、short、int、long、float、double、boolean、char)。  
          注:当 int 取值 -1~5 采用 iconst 指令,以及
          取值 -128~127 采用 bipush 指令-----不会放入常量池, 
          取值 -32768~32767 采用 sipush 指令,取值 -2147483648~2147483647 采用 ldc 指令。-----会放入常量池
        2. 符号引用-(类和接口的全限定名,方法和字段的名称和描述符-类型)
      复制代码

      image.png

  4. 访问标志:两个字节,描述该Class是类还是接口,以及被哪些修饰符修饰。
    例如Public=0x0001,多个修饰符则或(ACC_PUBLIC | ACC_FINAL,即0x0001 | 0x0010=0x0011)

  5. 当前类名:当前类的全限定名。
    两个字节,为常量池中的索引值,根据索引值可以在常量池中找到这个类的全限定名。

  6. 父类名称:父类的全限定名,同上。

  7. 接口信息:
    接口计数器,两个字节,描述了该类或父类实现的接口数量。紧接着的n个字节是所有接口名称的字符串常量的索引值。

  8. 字段表:字段表计数器+权限修饰符(private)+字段名索引+字段描述符索引+属性个数+属性列表

image.png

  1. 方法表:方法计数器+权限修饰符+方法名索引+描述符索引+属性个数+属性列表

     构造方法也是一个init方法。 
     方法的属性可以分为code区(存放着16进制操作码)+行号表+本地变量表,code区其实就是所说的字节码指令,
     十六进制值操作码与助记符的对应关系和用处可以查看Oracle官方文档了解
     
     JVM的指令集是基于栈而不是寄存器,基于栈可以具备很好的跨平台性(因为寄存器指令集往往和硬件挂钩)
     但是栈只是一个FILO结构,需要频繁的压栈出栈,并且栈是在内存中实现,  
     而寄存器是在CPU的高速缓冲区,相较而言基于栈的速度要慢很多。
    复制代码

image.png

  1. 附加属性表:该文件中类或接口所定义属性的基本信息。

参考资料:
字节码增强技术探索:tech.meituan.com/2019/09/05/…
Java常量池:blog.csdn.net/Viscu/artic…

© 版权声明
THE END
喜欢就支持一下吧
点赞0 分享