JVM概念

  • JVM是Java Virtual Machine的简称.意为Java虚拟机

  • 虚拟机

    指通过软件模拟的具有完整硬件系统功能的,运行在一个完全隔离环境中的完整计算机系统

  • 有哪些虚拟机

    • VMWare

    • Visual Box

    • JVM

  • VMWare或者Visual Box都是使用软件模拟物理CPU指令集

  • JVM使用软件模拟Java字节码的指令集

Java和JVM的历史

  • 1996年SUN JDK 1.0 Classic VM

    • 纯解释运行,使用外挂进行JIT
  • 1997年 JDK 1.1 发布

    • AWT,内部类,JDBC,RMI,反射
  • 1998年 JDK 1.2 Solaris Exact VM

    • JIT 解释器混合

    • Accurate Memory Management 精确内存管理,数据类型敏感

    • 提升了GC性能

    • JDK 1.2 开始成为Java2 J2SE J2EE J2ME出现 加入Swing Collections

  • 2000年 JDK 1.3 Hotspot 作为默认虚拟机发布

    • 加入JavaSound
  • 2002年 JDK 1.4 Classic VM 退出历史舞台

  • Assert 正则表达式 NIO IPV6 日志API 加密类库

  • 2004年发布 JDK1.5 即JDK5,J2SE 5,Java 5

    • 泛型

    • 注解

    • 装箱

    • 枚举

    • 可变长的参数

    • Foreach循环

  • JDK1.6 JDK6

    • 脚本语言支持

    • JDBC 4.0

    • Java编译器 API

  • 2011年 JDK7发布

    • 由于JDK7加入内容太多,项目规划出现问题直到2011年才发布,延误项目推出到JDK8

    • G1垃圾回收器

    • 动态语言增强

    • 64位系统中的压缩指针

    • NIO 2.0

  • 2014年 JDK8 发布

    • Lambda表达式

    • Stream

    • 语法增强 Java类型注解

  • 2016年 JDK9

    • 模块化 Java + REPL = jshell

    • 简化进程API

    • 轻量化JSON API

    • 货币API

    • 改善竞争锁

    • 分割代码缓存区

    • Smart Java Compilation项目

大事记

  • 使用最为广泛的JVM为HotSpot

  • HotSpot为Longview Technologies开发 被SUN收购

  • 2006年Java开源并建立OpenJDK

    • HotSpot成为SUN JDK和Open JDK中所带的虚拟机
  • 2008年Oracle收购BEA

    • 得到JRockit VM
  • 2010年Oracle收购SUN

    • 得到Hotspot
  • Oracle宣布在JDK8时整合JRockit和Hotspot,优势互补

    • 在Hotspot基础上,移植JRockit优秀特性

各式JVM

  • KVM

    • Sun发布

    • IOS Android前,广泛用于手机系统

  • CDC/CLDC HotSpot

    • 手机,电子书,Pad等电子设备上建立统一的Java编程接口

    • J2ME的重要组成部分

  • JRockit

    • BEA
  • IBM J9 VM

    • IBM内部
  • Apache Harmony

    • 兼容与JDK 1.5和JDK 1.6的Java程序运行平台

    • 与Oracle关系恶劣 退出JCP Java社区的分裂

    • OpenJDK出现后,受到挑战,2011年退役

    • 没有大规模商用经历

    • 对Android的发展有积极作用

规范

  • Java语言规范

    • 语法

    • 变量

    • 类型

    • 文法

  • JVM规范

    • Class文件类型

    • 运行时数据

    • 帧栈

    • 虚拟机的启动

    • 虚拟机的指令集

Java语言规范

  • 语法定义

    • IfThenStatement:

      if( Expression ) Statement

    • ArgumentList:

      Argument

      ArgumentList,Argument

  • 词法结构

    • \u + 4个16进制数字 表示UTF-16

    • 行终结符:CR or LF,or CR LF

    • 空白符

      空格 tab \t 换页 \f 行终结符

    • 注释

    • 标识符(变量、类、方法等命名的符号)

    • 关键字

    • int

      0 2 0372 0xData_Cafe 1996 0x00_FF__00_FF

      从JDK 1.7开始允许使用下划线分割数字

    • long

      0l 0777L 0x1000000000L 2_17_483_68L 0xC0B0L

    • float

      1e1f 2.f .3f 0f 3.1444f 6.022137e+23f

    • double

      1e1 2. .3 0.0 3.14 1e-9d 1e137

    • 操作

      += -= *= /= &= |= ^= %= <<= >>= >>>=

  • 类型和变量

    • 元类型

      byte short int long float char

    • 变量初始化

      boolean false

      char \u0000

    • 泛型

JVM规范

  • Java语言规范定义了什么是Java语言

  • Java语言和JVM行对独立

    • Gloovy

    • Clojure

    • Scala

  • JVM主要定义二进制class文件和JVM指令集

  • Class文件格式

  • 数字的内部表示和存储

    • byte -128 to 127 (-2^7 to 2^7 -1)
  • returnAddress 数据类型定义

    • 指向操作字节码的指针.不对应Java数据类型,不能在运行时修改.Finally实现需要
  • 定义PC(指令集寄存器)

  • 方法区

  • 整数的表达

    • 原码:第一位为符号位(0位正数,1为负数)

    • 反码:符号位不动,原码取反

    • 负数补码:符号位不动,反码加1

    • 正数补码:和原码相同

    • 打印整数的二进制表示

int a = -6;

for(int i=0;i<32;i++){
    int t = (a & 0x80000000 >>> i)>>>(31-i);
    System.out.print(t);
}
  • 为什么要用补码

    • 计算0的表示

    按照0是正数:00000000,负数:10000000,补码都为00000000没有歧义

    计算加分法直接用补码相加就可以了

  • float的表示与定义

  • 支持IEEE 754

    • s eeeeeeee mmmmmmmmmmmmmmmmmmmmm

      s为符号位,e为指数位(8位),m为尾数(23位)

    • e全0 尾数附加位为0 否则尾数附加位为1

    • sm2^(e-127)

-5

1100000010100000000000000000000000

-12^(129-127)(2^0+2^-2)

  • 一些特殊的方法

    • <clint>

      类的初始化方法,只有在类初始化的时候调用一次

    • <init>

      每初始化一个实例调用一次

  • VM指令集

    • 类型转换

      l2i(long-->int)

    • 出栈入栈操作

      aload astore

    • 运算

      iadd isub

    • 流程控制

      ifeq ifne

    • 函数调用

      invokevirtual invokeinterface invokespecial invokestatic

  • JVM需要对Java Library提供以下支持

    • 反射 java.lang.reflect

    • ClassLoader

    • 初始化class和interface

    • 安全相关 java.security

    • 多线程

    • 弱引用

  • JVM的编译

    • 源码到JVM指令对应格式

    • javap(反编译器)

    • JVM反汇编格式

      <index><opcode>[<operand1>[operand2...]][<comment>] (index:索引,opcode:操作码,operand:操作数,comment:注释)

实例

void spin(){
    int i;
    for(i=0;i<100;i++){
        ;
        //Loop body is empty
    }
}

0 iconst_0 //Push int constant 0

1 istore_1 //Store into local variable 1 (i=0)

2 goto 8 //First time throught don't increment

5 iinc 1 1 //Increment local variable 1 by 1(i++)

8 iload_1 //Push local variable 1(i)

9 bipush 100 //Push int constant 100

11 if_icmplt 5 //Compare and loop if less than(i<100)

14 return //Return void when done