首页 > 代码库 > Java8_从Permanent Generation到Metaspace

Java8_从Permanent Generation到Metaspace

Java8_从Permanent Generation到Metaspace


Java8已经移除了永久代(Permanent Generation)的内存区域,而出现了新的内存区域元空间(Metaspace)。


Permanent Generation

这块内存主要保存什么?

So the Java classes are stored in the permanent generation. What all does that entail? Besides the basic fields of a Java class there are

  • Methods of a class (including the bytecodes)

  • Names of the classes (in the form of an object that points to a string also in the permanent generation)

  • Constant pool information (data read from the class file, see chapter 4 of the JVM specification for all the details).

  • Object arrays and type arrays associated with a class (e.g., an object array containing references to methods).

  • Internal objects created by the JVM (java/lang/Object or java/lang/exception for instance)

  • Information used for optimization by the compilers (JITs)


常见的OOM异常:OutOfMemoryError: PermGen space

    这往往是由类加载器相关的内存泄漏以及新类加载器的创建导致的,通常出现于代码热部署时。相对于正式产品,该问题在开发机上出现的频率更高,正是这个原因。当它在产品中出现时,开发者可以拿到生成的堆转储文件,并利用像Eclipse Memory Analyzer Toolkit这样的工具来寻找应该卸载却没被卸载的类加载器。除非通过特定配置阻止,PermGen也是会进行垃圾回收的。然而,在出现内存泄漏时,就没什么可回收的了。


相关的JVM参数:(jdk7)

-XX:MaxPermSize=64m Size of the Permanent Generation.  [5.0 and newer: 64 bit VMs are scaled 30% larger; 1.4 amd64: 96m; 1.3.1 -client: 32m.]

在jdk8中,相关的参数已经不被使用:

-XX:MaxPermSize=size

Sets the maximum permanent generation space size (in bytes). This option was deprecated in JDK 8, and superseded by the -XX:MaxMetaspaceSize option.

-XX:PermSize=size

Sets the space (in bytes) allocated to the permanent generation that triggers a garbage collection if it is exceeded. This option was deprecated un JDK 8, and superseded by the -XX:MetaspaceSize option.


Metaspace

    Java 8中再也没有PermGen了。其中的某些部分,如被intern的字符串,在Java 7中已经移到了普通堆里。其余结构在Java 8中会被移到称作“Metaspace”的本机内存区中,该区域在默认情况下会自动生长,也会被垃圾回收。它有两个标记:MetaspaceSize和MaxMetaspaceSize。


相关的JVM参数:

-XX:MetaspaceSize=size

Sets the size of the allocated class metadata space that will trigger a garbage collection the first time it is exceeded. This threshold for a garbage collection is increased or decreased depending on the amount of metadata used. The default size depends on the platform.

-XX:MaxMetaspaceSize=size

Sets the maximum amount of native memory that can be allocated for class metadata. By default, the size is not limited. The amount of metadata for an application depends on the application itself, other running applications, and the amount of memory available on the system.

The following example shows how to set the maximum class metadata size to 256 MB:-XX:MaxMetaspaceSize=256m


PermGen space situation

This memory space is completely removed.

The PermSize and MaxPermSize JVM arguments are ignored and a warning is issued if present at start-up.


Metaspace memory allocation model

Most allocations for the class metadata are now allocated out of native memory.

The klasses that were used to describe class metadata have been removed.


Metaspace capacity

By default class metadata allocation is limited by the amount of available native memory (capacity will of course depend if you use a 32-bit JVM vs. 64-bit along with OS virtual memory availability).

A new flag is available (MaxMetaspaceSize), allowing you to limit the amount of native memory used for class metadata. If you don’t specify this flag, the Metaspace will dynamically re-size depending of the application demand at runtime.


Metaspace garbage collection

Garbage collection of the dead classes and classloaders is triggered(触发的) once the class metadata usage reaches the “MaxMetaspaceSize”.

Proper monitoring & tuning of the Metaspace will obviously be required in order to limit the frequency or delay of such garbage collections. Excessive Metaspace garbage collections may be a symptom of classes, classloaders memory leak or inadequate sizing for your application.


Java heap space impact

Some miscellaneous data has been moved to the Java heap space. This means you may observe an increase of the Java heap space following a future JDK 8 upgrade.


Metaspace monitoring

Metaspace usage is available from the HotSpot 1.8 verbose GC log output.

Jstat & JVisualVM have not been updated at this point based on our testing with b75 and the old PermGen space references are still present.

====END====


Java8_从Permanent Generation到Metaspace