Warning: file_get_contents(/data/phpspider/zhask/data//catemap/3/templates/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
java 8 java.lang.OutOfMemoryError:Metaspace_Java_Out Of Memory - Fatal编程技术网

java 8 java.lang.OutOfMemoryError:Metaspace

java 8 java.lang.OutOfMemoryError:Metaspace,java,out-of-memory,Java,Out Of Memory,运行Java cs应用程序时出现OutOfMemoryError。根据错误消息,似乎错误发生在将XML字符串传输到Java对象时 传输代码如下所示 public static Object convertXmlStrToObject(Class clazz, String xmlStr) { Object xmlObject = null; try { JAXBContext context = JAXBContext.newInstance(clazz);

运行Java cs应用程序时出现OutOfMemoryError。根据错误消息,似乎错误发生在将XML字符串传输到Java对象时

传输代码如下所示

public static Object convertXmlStrToObject(Class clazz, String xmlStr) {
    Object xmlObject = null;
    try {
        JAXBContext context = JAXBContext.newInstance(clazz);
        // 进行将Xml转成对象的核心接口
        Unmarshaller unmarshaller = context.createUnmarshaller();
        StringReader sr = new StringReader(xmlStr);
        xmlObject = unmarshaller.unmarshal(sr);
    } catch (JAXBException e) {
        e.printStackTrace();
    }
    return xmlObject;
}
我已经查看了日志,找到了触发此错误的字符串。 然后我使用上面的代码将这个字符串转换成java对象,大约转换了10K次,没有报告任何错误

我有数千个这样的应用程序在windows xp系统中运行,我担心这可能会导致一个巨大的问题。我在谷歌上搜索了这个错误,很多人说这个错误是因为MaxMetaspaceSize太小,而我在应用程序中没有使用MaxMetaspaceSize

java.lang.OutOfMemoryError: Metaspace
    at com.sun.org.apache.xerces.internal.jaxp.SAXParserImpl.<init>(Unknown Source)
    at com.sun.org.apache.xerces.internal.jaxp.SAXParserFactoryImpl.newSAXParser(Unknown Source)
    at com.sun.xml.internal.bind.v2.runtime.unmarshaller.UnmarshallerImpl.getXMLReader(Unknown Source)
    at javax.xml.bind.helpers.AbstractUnmarshallerImpl.unmarshal(Unknown Source)
    at javax.xml.bind.helpers.AbstractUnmarshallerImpl.unmarshal(Unknown Source)
    at com.hgits.payCodeDebit.util.XMLUtil.convertXmlStrToObject(XMLUtil.java:91)
谷歌搜索之后,这似乎是一个记忆问题。 我用jna和windows api GetProcessMemoryInfo耗尽了进程内存。 当我的应用程序启动时,jvm进程内存是615616K,这是正常的,一切正常。运行大约36小时后,jvm进程内存达到1796676K,我开始出现“java.lang.OutOfMemoryError:Map failed”错误。 当jvm进程内存达到1796676K时,我还记录了jvm的堆内存,它低于810942464byte(Runtime.getRuntime().maxMemory()):810942464byte(Runtime.getRuntime().totalMemory()):239632736byte(Runtime.getRuntime().freemory())。 所以jvm堆中仍然有2亿可用内存

因为我使用jna加载了几个dll,所以我猜测在一些dll中存在某种内存泄漏。
如果我的猜测是正确的,我如何找到原因?我试过jjvisualvm和jmc,但没有发现任何错误。

我可以想出一些解释:

  • 一些XML解析器习惯于插入字符串。如果您正在进行大量XML解析,这会将大量字符串数据放入字符串池。。。在元空间中。如果字符串仍然是可访问的(例如,因为DOM是可访问的,或者因为您将它们保存在另一个数据结构中),则可以填充元空间

  • 在幕后,应用程序中的某些内容可能会进行大量的类加载。例如,如果广泛使用动态代理。这可以将大量不可收集的类放入元空间,最终填充它

  • 动态代理(见上一点)可能是由
    JAXBContext
    初始化创建的。正如@PaulBastide所指出的,您应该能够创建一个
    JAXBContext
    并重用它。这样做不仅可以提高效率,还可以解决元空间泄漏问题

  • 增加Meta SPACE的大小是一个创可贴解决方案。一个更好的方法是让JVM在OOME出现时创建一个堆转储,并分析该转储以找出是什么占用了这么多的元空间。然后决定是否是一个你可以解决的问题,或者是使用<代码> -XX:Meta AsAsCase=…创可贴,还是希望最好。


    这已经很晚了,但是您导致
    java.lang.OutOfMemoryError:Map failed
    的问题不是普通的内存泄漏;i、 e.Java堆对象或本机堆对象泄漏。这可能根本不是一个漏洞

    发生的情况是,您的代码正在尝试将文件映射到内存中。JVM要求操作系统提供一个大内存段来保存文件,操作系统说“不”。原因可能有很多:

  • 您试图映射的文件可能太大
  • 您的应用程序可能已经映射了许多其他文件,但未能取消映射。(那将是一个漏洞。)
  • JVM进程上可能有“ulimit”或类似的限制
  • 如果您运行的是32位JVM,则可能会遇到32位虚拟地址空间限制

  • 我可以想出几个解释:

  • 一些XML解析器习惯于插入字符串。如果您正在进行大量XML解析,这会将大量字符串数据放入字符串池。。。在元空间中。如果字符串仍然是可访问的(例如,因为DOM是可访问的,或者因为您将它们保存在另一个数据结构中),则可以填充元空间

  • 在幕后,应用程序中的某些内容可能会进行大量的类加载。例如,如果广泛使用动态代理。这可以将大量不可收集的类放入元空间,最终填充它

  • 动态代理(见上一点)可能是由
    JAXBContext
    初始化创建的。正如@PaulBastide所指出的,您应该能够创建一个
    JAXBContext
    并重用它。这样做不仅可以提高效率,还可以解决元空间泄漏问题

  • 增加Meta SPACE的大小是一个创可贴解决方案。一个更好的方法是让JVM在OOME出现时创建一个堆转储,并分析该转储以找出是什么占用了这么多的元空间。然后决定是否是一个你可以解决的问题,或者是使用<代码> -XX:Meta AsAsCase=…创可贴,还是希望最好。


    这已经很晚了,但是您导致
    java.lang.OutOfMemoryError:Map failed
    的问题不是普通的内存泄漏;i、 e.Java堆对象或本机堆对象泄漏。这可能根本不是一个漏洞

    发生的情况是,您的代码正在尝试将文件映射到内存中。JVM要求操作系统提供一个大内存段来保存文件,操作系统说“不”。原因可能有很多:

  • 您试图映射的文件可能太大
  • 您的应用程序可能已经映射了许多其他文件,但未能取消映射。(那将是一个漏洞。)
  • JVM进程上可能有“ulimit”或类似的限制
  • 如果您运行的是32位JVM,则可能会遇到32位虚拟地址空间限制
  • JAXBContext应该始终是静态的,它是线程安全的
    java.io.IOException: Map failed
    at sun.nio.ch.FileChannelImpl.map(Unknown Source)
    at sun.nio.ch.FileChannelImpl.transferFromFileChannel(Unknown Source)
    at sun.nio.ch.FileChannelImpl.transferFrom(Unknown Source)
    at org.apache.commons.io.FileUtils.doCopyFile(FileUtils.java:1147)
    at org.apache.commons.io.FileUtils.copyFile(FileUtils.java:1091)
    at org.apache.commons.io.FileUtils.copyFile(FileUtils.java:1038)
    at com.hgits.cron.CheckNonFareParamJob.checkRecvParamList(CheckNonFareParamJob.java:153)
    at com.hgits.cron.CheckNonFareParamJob.execute(CheckNonFareParamJob.java:54)
    at org.quartz.core.JobRunShell.run(JobRunShell.java:213)
    at org.quartz.simpl.SimpleThreadPool$WorkerThread.run(SimpleThreadPool.java:557)
    Caused by: java.lang.OutOfMemoryError: Map failed
    at sun.nio.ch.FileChannelImpl.map0(Native Method)
    ... 10 more