JVM 虚拟机系列:内存结构之栈区(虚拟机栈中的栈帧结构之局部变量表)

javap -c命令详解_junsure2012-CSDN博客_javap命令一直在学习Java,碰到了很多问题,碰到了很多关于i++和++i的难题,以及最经典的String str = "abc" 共创建了几个对象的疑难杂症。 知道有一日知道了java的反汇编 命令  javap。现将学习记录做一小结,以供自己以后翻看。如果有错误的地方,请指正1.javap是什么: where options include:-c Disassemble thhttps://blog.csdn.net/junsure2012/article/details/7099222

javap是jdk自带的反解析工具。它的作用就是根据class字节码文件,反解析出当前类对应的code区(汇编指令)、本地变量表、异常表和代码行偏移量映射表、常量池等等信息。 

public class TestDate {
   
    public static void main(String[] args) {
        int i = 2;
		int j = 3;
    }
}

 通过javap 反解析字节码文件得到下面结果:

  Code:
   0:   iconst_2    //把2放到栈顶
   1:   istore_1    //把栈顶的值放到局部变量1中,即i中
   2:   iconst_3    //把3放到栈顶
   3:   istore_2    //把栈顶的值放到局部变量1中,即j中
   4:   return

对于 int i = 2;首先它会在栈中创建一个变量为i的引用,然后查找有没有字面值为2的地址,没找到,就开辟一个存放2这个字面值的地址,然后将i指向2的地址

请查看 JVM字节码指令表

JVM虚拟机字节码指令表_android的专栏-CSDN博客https://blog.csdn.net/u013620306/article/details/122961698

操作数栈(Operand Stack)也常称为操作栈,它是一个后入先出栈(LIFO)。同局部变量表一样,操作数栈的最大深度也在编译的时候写入到方法的Code属性的max_stacks数据项中
当一个方法刚刚开始执行时,其操作数栈是空的,随着方法执行和字节码指令的执行,会从局部变量表或对象实例的字段中复制常量或变量写入到操作数栈,再随着计算的进行将栈中元素出栈到局部变量表或者返回给方法调用者,也就是出栈/入栈操作。一个完整的方法执行期间往往包含多个这样出栈/入栈的过程。

这里引申出两个问题 

1:怎么查看局部变量表

2:操作数栈 ---局部变量表 --PC寄存器工作过程

jvm代码深入追踪-操作数栈-局部变量表-pc寄存器的执行过程_水巷石子的博客-CSDN博客public class OperandStackTest { public void testAddOperation() { byte i = 15; int j = 8; int k = i + j; }byte、short、char、boolean:都是int型来保存的(当然int本身也是用int型来保存的),long和double都是占64位。所以在jclasslib中存的是用int类型存储的,bipush。取的时候,也是用https://blog.csdn.net/qq_37924905/article/details/109865893

第二个问题研究:

我们先写一个程序 :

public class OperandStackTest {
    
	public static void main(String[] args) {
        byte i = 15;
        int j = 8;
        int k = i + j;
    }
}

经过  javap -c 反编译之后得到如下结果

1.首先pc寄存器存的指令地址为0,所以执行bipush操作指令,将byte类型的15转为int类型压入操作数栈。

2.然后pc寄存器的指令地址变为2,则执行istore_1操作指令,意思是将上面的15存在局部变量表的下标为1的位置。有人可能会问,为什么局部变量表会从1开始,而不是从0开始。

 3.pc寄存器指令地址为3,执行操作指令bipush,将8再压入栈中。

4.pc寄存器指令地址5,执行操作指令istore_2,将栈顶的8存入局部变量表2的位置

5.pc寄存器指令地址为3,执行操作指令bipush,将8再压入栈中。

6.pc寄存器指令地址5,执行操作指令istore_2,将栈顶的8存入局部变量表2的位置

7.pc寄存器指令地址为8,执行操作指令iadd,意思就是将操作数栈中的两个数进行出栈相加后再压栈,也就是8+15=23,将23再压栈,如上图。(这里的相加是通过执行引擎,最终在cpu相加,具体看后面文章,这边先不细说)

8.pc寄存器指令地址为9,执行操作指令istore_3,意思就是将操作数栈顶元素23存入局部变量表中位置为3的地方。

9. 最终一步return 返回
 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值