• JVM-class文件完全解析-字段表集合


     字段表集合

      这个class文件的解析,分析得有点太久了.前面介绍类魔数,次版本号,主板本号,常量池入口,常量池,访问标志,类索引,父类索引和接口索引集合.下面就应该到字段表集合了. 

      紧接着接口索引集合的就是字段表的集合了.

      字段表(field_info)用于描述接口或者类中声明的变量.字段包括类级变量以及实例级变量,但是不包括在方法内部声明的局部变量.

      字段表的结构:

    类型     名称 数量
    u2 access_flags 1
    u2 name_index 1
    u2 descriptor_index 1
    u2 attributes_count 1
    attribute_info attributes attributes_count

      字段修饰符放在access_flags项目中,它与类中的access_flags项目是非常相似的,都是一个u2的数据类型.

      字段访问标志:

    标志名称 标志值 含义
    ACC_PUBLIC 0x00 01 字段是否为public
    ACC_PRIVATE 0x00 02 字段是否为private
    ACC_PROTECTED 0x00 04 字段是否为protected
    ACC_STATIC 0x00 08 字段是否为static
    ACC_FINAL 0x00 10 字段是否为final
    ACC_VOLATILE 0x00 40 字段是否为volatile
    ACC_TRANSTENT 0x00 80 字段是否为transient
    ACC_SYNCHETIC 0x10 00 字段是否为由编译器自动产生
    ACC_ENUM 0x40 00 字段是否为enum

      跟随access_flags标志的是两项索引值:name_index和descriptor_index,它们都是对常量池的引用,分别代表着字段的简单名称以及字段方法和方法的描述符.

      描述符的作用是用来描述字段的数据类型,方法的参数列表(包括数量,类型以及顺序)和返回值.根据描述符规则,基本数据类型以及代表无返回值的void类型都用一个大写字符来表示,而对象类型则用字符加L加对象名的全限定名来表示.

      描述符标志含义:

      

    标志符 含义
    B 基本数据类型byte
    C 基本数据类型char
    D 基本数据类型double
    F 基本数据类型float
    I 基本数据类型int
    J 基本数据类型long
    S 基本数据类型short
    Z 基本数据类型boolean
    V 基本数据类型void
    L 对象类型

      对于数组类型,每一维度将使用一个前置的"["字符来描述.如一个定义为"java.lang.Stirng[ ]"类型的二维数组,将被记录为:"[[Ljava/lang/Stirng",一个整型数组"int[]"将被记录为"[I".

      用描述符来描述方法时,按照先参数列表,后返回值的顺序来描述,参数列表按照参数的严格顺序放在一组小括号"()"之内.

      字段表集合中不会列出从父类或者父接口中继承而来的字段,但有可能列出原来Java代码中不存在的字段,譬如在内部类中为了保持对外部类的访问性,会自动添加指向外部类实例的字段.另外,在Java语言中字段是无法重载的,两个字段的数据类型,修饰符不管是否相同,都必须使用不一样的名称,但是对于字节码来讲,如果连个字段的描述符不一致,那字段重名就是合法的.

     

       下面继续前面分析的class文件:

      源文件:

      

      javap分析出来的常量池:

      

      分析:  

       从上图中分析可以看到0x00 01表示字段表数据的个数,只有一个.0x00 02表示字段表的private修饰符,从上面的字段访问标志表可以看到.0x00 05表示字段对应着第5个常量池,从javap分析出来的常量池,可以看到第5个常量池对应着m,再看源代码我们定义的字段确实就是m.0x00 06表示描述符标识,对应着第6个常量池,为I,那么在对应我们的访问标识符含义表,I 对应着int数据类型,再看源代码m的数据类型确实就是int.

  • 相关阅读:
    js如何识别后端返回的“↵”,让其换行
    ReactNative插件
    ReactNative踩坑
    js对当前时间进行处理
    vue-awesome-swiper手动滑动后不再自动轮播的问题
    HTML5知识点汇总
    懒加载的实现原理及一些实现方法
    使用node.js实现多人聊天室(socket.io、B/S)
    [vue学习] 卡片展示分行功能简单实现
    [vue学习]快速搭建一个项目
  • 原文地址:https://www.cnblogs.com/lrh-xl/p/5350612.html
Copyright © 2020-2023  润新知