java 虚拟机指令集_jvm规范-jvm虚拟指令集及编译

第六章:jvm虚拟指令集

6.1假定:“必须”的含义

对于jvm指令的一些“必须”的要求,在运行期要求javaclass的结构是满足约束的,对于不满足约束的情况,jvm的行为是未定义的。

6.2保留操作码

在java class文件中使用的指令操作码,有三个操作码是保留的,供java虚拟机内部使用。

254(0xfe)和255(0xff),分别有助记符impdep1和impdep2,目的是在软件或者硬件实现的特定功能提供“后门”或陷阱。

202(0xca),有助记符breakpoint,目的是由调试程序使用来实现断点。

6.3虚拟机错误

当内部错误或者资源限制导致java语言语义不能实现时,jvm抛出一个VirtualMachineError类的子类的实例。jvm规范不规定和语言抛出的时间和地点。

6.4jvm指令集

我不一一例举各种指令的操作码和用法,需要时去查就行了。

第七章 为jvm编译

7.1范例格式

java编译成为class文件之后,以类汇编的jvm操作指令方式存在,jdk自带的javap程序具有这样的功能,将class文件翻译为这样的指令集。

下面是我测试的一个实例:

源文件为test.java

public class test {

public static String a = "";

public int i =0;

public test() {

int i=0;

String a = "xyz";

}

}

编译完成为test.class,用javap生成之后输出结果为:

C:\JBuilderX\jdk1.4\bin>javap -c  -classpath "c:/" test

Compiled from "test.java"

public class test extends java.lang.Object{

public static java.lang.String a;

public int i;

static {};

Code:

0:   ldc     #4; //String

2:   putstatic       #5; //Field a:Ljava/lang/String;

5:   nop

6:   return

public test();

Code:

0:   aload_0

1:   invokespecial   #1; //Method java/lang/Object."":()V

4:   aload_0

5:   iconst_0

6:   putfield        #2; //Field i:I

9:   iconst_0

10:  istore_1

11:  ldc     #3; //String xyz

13:  astore_2

14:  nop

15:  return

}

7.2常数、局部变量和控制结构的使用

jvm是面向栈的,大多数操作都是从当前框架的操作数栈中取得操作数。

7。3运算

jvm一般在操作数栈上进行运算,即从栈中取操作数,并将结果存入操作数栈中。

7。4访问常数池

byte,char,short,以及小int值都可以通过立即数的方式编译在method的code中,但是int,long,float,double,以及string实例的引用,就需要对常数池进行访问了。使用ldc,ldc_w,ldc2_w指令管理。

7.5更多控制范例

可供查阅

7。6接收参数

如果向java实例方法传递了n个参数,它们被接收,按约定,框架的编号1到n的局部变量为新的方法调用创建,顺序为接收的顺序。

7。7调用方法

对java实例方法的调用,是在对象的运行期类型上调度的。用invokevirtual实现,将其参数取做对常数池表项的索引,给出对象的类类型的完整限定符名称,再调用方法的名称和方法的描述符。

对java静态(类)方法的调用,无需传递类实例,其余和实例方法相似,用invokespecial方法实现。

invokespecail指令用于调用实例初始化方法。超类方法和调用private方法。

7。8处理类实例

构建一个类实例的过程,在建立对象及其实例域之后,用invokespecial调用相应构造函数对应的方法来初始化对象。

对对象域的访问用getfield和putfield指令完成。

7。9数组

主要讲的是数组操作的相关jvm指令,如:newarray,过一遍,可以查阅。

7。10编译开关

对于java的switch指令,jvm有对应的两种指令:tableswitch,lookupswitch.

tableswitch指定取值范围,而lookupswitch并不指定取值范围,两者如何选择完全由效率选择决定。

7。11对操作数栈的操作

jvm有大量的指令补充,将操作数栈的内容作为无类型字或成对的无类型字操纵。便于jvm虚拟机指令的灵活组成。

如dup,dup_x2等,都是对字或者双字进行操作。

7。12抛出或者处理异常

jvm中try...catch块的处理对于jvm指令处理是透明的,辅助控制是由异常表来完成的,由异常表来决定到哪里去调用处理,哪些部分的异常是受控的。

7。13编译finally

try.....finally语句与try-catch相似,只是其辅助控制是由指令jsr(子例程调用)显式的表示,在jsr调用之前,将下一指令的地址压入栈中。而异常表只控制try块的范围。

7。14同步

jvm用monitorenter和monitorexit指令对同步提供显式支持。而java常用sychronized方法。

sychronized“方法”通常不是用monitorenter和monitorexit指令实现的。往往是由“方法调用指令”检查常数池里的ACC_SYCHRONIZED标志

但monitorenter和monitorexit指令是为了支持sychronized“语句”而存在的。

注意这里的方法和语句的区别。

语句实例如下:test.java

public class test {

public test() {

}

public static void main(String[] args) {

synchronized(new Object()){

int i = 0;

}

}

}

编译完的结果:

C:\JBuilderX\bin>javap -c  -classpath "d:/epm40/classes" test

Compiled from "test.java"

public class test extends java.lang.Object{

public test();

Code:

0:   aload_0

1:   invokespecial   #1; //Method java/lang/Object."":()V

4:   nop

5:   return

public static void main(java.lang.String[]);

Code:

0:   new     #2; //class Object

3:   dup

4:   invokespecial   #1; //Method java/lang/Object."":()V

7:   dup

8:   astore_1

9:   monitorenter

10:  iconst_0

11:  istore_2

12:  nop

13:  aload_1

14:  monitorexit

15:  goto    23

18:  astore_3

19:  aload_1

20:  monitorexit

21:  aload_3

22:  athrow

23:  nop

24:  return

Exception table:

from   to  target type

10    15    18   any

18    21    18   any

}

而synchronized方法编译没有特殊之处,只是在方法名上加了synchronzied字样。

From:http://www.blogjava.net/flyffa/archive/2006/08/24/65566.html

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

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值