Github仓库地址:https://github.com/Damaer/Jvm...
文档地址:https://damaer.github.io/JvmN...
JVM生命周期
- 启动
- 执行
- 退出
启动
Java虚拟机的启动时通过疏导加载器(bootstrap class loader
)创立一个初始类(initial class
)来实现的,这个类是由Java虚拟机的具体实现指定的。
自定义的类是由零碎类加载器加载的。自定义类的顶级父类都是Object
,Object
作为外围api
中的类,是须要被疏导加载器(bootstrap class loader
)加载的。父类的加载是优先于子类加载的,所以要加载自定义的之前,会就加载Object
类。
执行
Java
虚拟机执行的时候有一个清晰的工作:执行Java
程序。- 真正执行程序的是一个叫
Java虚拟机
的过程。
退出
虚拟机的退出有以下几种状况:
- 程序失常执行完结
- 程序执行过程中遇到了异样或者谬误而异样终止
- 因为操作系统呈现谬误而导致Java虚拟机过程终止
- 某线程调用
Runtime
类或者System
类的exit
办法,或者Runtime
类的halt()
办法,并且Java
平安管理器也容许这次操作的条件下。 JNI
(java native Interface
):用JNI
的api
加载或者卸载Java
虚拟机的时候,Java
虚拟机可能异样退出。
System.exit()和Runtime.halt()
上面剖析System.exit()和Runtime.halt():
System.exit()
其实调用的是Runtime
对象的exit()
办法,Runtime.getRuntime()
获取的是以后的运行时状态,也就是Runtime
对象。
public static void exit(int status) { Runtime.getRuntime().exit(status); }
看Runtime
的exit()
办法,外面调用的是Shutdown.exit(status)
。
public void exit(int status) { SecurityManager security = System.getSecurityManager(); if (security != null) { security.checkExit(status); } Shutdown.exit(status); }
咱们看Shutdown
的exit()
办法,当status不为0的时候,调用的是halt(status)
。
static void exit(int status) { boolean runMoreFinalizers = false; synchronized (lock) { if (status != 0) runFinalizersOnExit = false; switch (state) { case RUNNING: /* Initiate shutdown */ state = HOOKS; break; case HOOKS: /* Stall and halt */ break; case FINALIZERS: if (status != 0) { /* Halt immediately on nonzero status */ halt(status); } else { /* Compatibility with old behavior: * Run more finalizers and then halt */ runMoreFinalizers = runFinalizersOnExit; } break; } } if (runMoreFinalizers) { runAllFinalizers(); halt(status); } synchronized (Shutdown.class) { /* Synchronize on the class object, causing any other thread * that attempts to initiate shutdown to stall indefinitely */ sequence(); halt(status); } }
而halt(int status)
实质上调用的是一个本地办法halt0(int status)
,暂停虚拟机过程,退出。
static void halt(int status) { synchronized (haltLock) { halt0(status); } } static native void halt0(int status);
Runtime
是运行时数据的对象,全局单例的,能够了解为它代表了运行时数据区。是一个饿汉式单例模式。从 JDK1.0 开始就,能够看出,这就是虚拟机的外围类!
上面能够测试一下Runtime
的属性:
public class RuntimeTest { public static void main(String[] args) { Runtime runtime = Runtime.getRuntime(); System.out.println(runtime.getClass().getName()); System.out.println("maxMemory: "+runtime.maxMemory()/1024/1024); System.out.println("totalMemory: "+runtime.totalMemory()/1024/1024); System.out.println("freeMemory: "+runtime.freeMemory()/1024/1024); }}
运行后果:示意最大的内存是2713M,总的内存是184M,能够应用内存是180M。
java.lang.RuntimemaxMemory: 2713totalMemory: 184freeMemory: 180
PS:本笔记是在宋红康老师的JVM视频中学习的笔记,均通过实际,加上本人的了解。地址:https://www.bilibili.com/vide... ,强烈推荐!!!
【作者简介】:
秦怀,公众号【秦怀杂货店】作者,技术之路不在一时,山高水长,纵使迟缓,驰而不息。这个世界心愿所有都很快,更快,然而我心愿本人能走好每一步,写好每一篇文章,期待和你们一起交换。