如何使用maven jvmArg解决“GC overhead limit exceeded”问题?

36

运行一个类时,我遇到了以下异常:

Exception in thread "main" java.lang.OutOfMemoryError: GC overhead limit exceeded

我尝试从类包的maven pom.xml中增加jvmArg堆大小:

http://maven.apache.org/xsd/maven-4.0.0.xsd"> 4.0.0

<parent>
    (...)
</parent>


<artifactId>(...)</artifactId>
<name>(...)</name>

<properties>
    <javaOpts.Xmx>4g</javaOpts.Xmx> <!-- default that can be adjusted on the command line with -DjavaOpts.Xmx=... -->
    <(...).basedir>${project.basedir}/..</(...).basedir>
</properties>

<build>
    <plugins>
        <plugin>
            <groupId>net.alchim31.maven</groupId>
            <artifactId>scala-maven-plugin</artifactId>
            <configuration>
                <launchers>
                    <launcher>
                        <id>MyClassName</id>
                        <mainClass>(...)</mainClass>
                        <jvmArgs>
                            <jvmArg>-Xmx${javaOpts.Xmx}</jvmArg>
                        (...) 

我已经尝试了最后一行的许多值:

  • <jvmArg>-Xmx512m{javaOpts.Xmx}</jvmArg>
  • <jvmArg>-Xmx4096M{javaOpts.Xmx}</jvmArg>
  • ...
  • <jvmArg>-Xmx10000000000M{javaOpts.Xmx}</jvmArg>

但对于它们中的所有值,我都遇到了相同的错误。

有人可以帮我吗? 注意:我正在使用 IntelliJ IDEA运行。


1
Maven与“运行”无关。如果您的问题是在运行应用程序时出现内存不足的情况,则需要在启动时设置堆大小参数,而不是在构建时使用maven。如果我误解了,请更新您的问题。 - Hilikus
我猜这是个错误:<jvmArg>-Xmx512m{javaOpts.Xmx}</jvmArg>,你真正想要的是 <jvmArg>-Xmx512m</jvmArg> - Pablo Mendes
7个回答

49

Java 7

这不是Maven的问题,你需要为虚拟机分配更多内存。您可以通过环境变量来实现这一点,而Maven启动器会在加载时自动选择这些设置,并使用它们来配置底层的Java虚拟机。

简单的方法是:

export MAVEN_OPTS="-Xmx1024M -Xss128M -XX:MaxPermSize=1024M -XX:+CMSClassUnloadingEnabled"

Windows:

set MAVEN_OPTS=-Xmx1024M -Xss128M -XX:MaxPermSize=1024M -XX:+CMSClassUnloadingEnabled

(没有双引号)

Java 8

Java 8已经用元空间替换了永久代,新的设置如下:

export MAVEN_OPTS="-Xmx1024M -Xss128M -XX:MetaspaceSize=512M -XX:MaxMetaspaceSize=1024M -XX:+CMSClassUnloadingEnabled"


4
这应该添加到您的shell环境中,而不是pom.xml文件中。 - Marco
将“set MAVEN_OPTS=-Xms1024M -Xmx2048M -XX:-UseGCOverheadLimit”行添加到您的“mvn.bat”文件作为第一行代码。 “mvn.bat”可以在C:\MAVEN_INSTALLATION_DIRECTORY\bin中找到。如果您使用的是Unix平台,则应编辑mvn.sh而不是mvn.bat。您可以根据程序运行/编译/构建所需的内存量更改-Xms和-Xmx值。 - HIREN011
请注意:Java 8中已删除MaxPermSize选项,现在将被忽略。 - Tony Laidig
@flavian,你的回答有错误。我认为你想说的是 -Xms128m 而不是 -Xss128m - 这对于每个线程来说是一个巨大的堆栈大小。 - devstructor
这是我的一个Maven问题。通常在3分钟内完成的工作,现在失败了30分钟。 - Philip Rego

10
我有一个类似的问题:我的项目工作区由超过250个Maven模块组成,当在IDEA中打开pom.xml时,<project><parent>标签会被用红色下划线标出,并且当将鼠标悬停在错误标记上时会显示以下错误信息:

java.lang.OutOfMemoryError: GC overhead limit exceeded

我的解决方案
  • >设置 >构建、执行、部署 >构建工具 >Maven >导入中设置高值,例如-Xmx1g以及
  • 更改>设置 >构建、执行、部署 >构建工具 >Maven(Maven主目录)下的maven实现,从(捆绑的)Maven 3更改为我的本地maven安装(不是与IDEA捆绑的那个),例如更改为/opt/maven/apache-maven-3.3.9Maven Settings Screenshot
由于我之前曾遇到过捆绑的maven问题,所以我不信任捆绑的maven。

1
在Maven:导入界面上添加堆大小选项(但保留捆绑的Maven 3),当我尝试在IntelliJ中导入整个wildfly-swarm项目时,这对我很有效。 - Frans

7

在上面的最佳答案中添加并行垃圾回收可能是最好的选择:

-Xmx2048M -Xss128M -XX:MaxPermSize=2048M -XX:+CMSClassUnloadingEnabled -XX:+UseConcMarkSweepGC

2

非常抱歉回复很晚,但我认为我的回答可能也会帮助其他人。

scala-maven-plugin无法使用MAVEN_OPTS增加内存,唯一的方法是在插件配置中使用jvmArgs。但要将jvmArgs放在配置部分而不是启动器部分中,就像这样:

<configuration>
    <jvmArgs>
        <jvmArg>-Xmx1024m</jvmArg>
        <jvmArg>-Xms256m</jvmArg>
    </jvmArgs>
</configuration>

这对我来说有效。


2

在某些情况下,您可以禁用垃圾回收限制:

-XX:-UseGCOverheadLimit

2
在我的情况下,只是得到了 java.lang.OutOfMemoryError: Java 堆空间。:-/ - Krzysztof Jabłoński
1
禁用它只会延迟问题,而不是减轻它。 - Snehasish

0

你正在将jvmArgs添加到pom.xml中的maven-scala-plugin配置中。

你说你是从IntelliJ IDEA运行的?你具体是怎么做的?通过他们的构建/运行,你根本没有使用Maven!然后更改pom.xml中的maven-scala-plugin启动器基本上是无用的。要更改IntelliJ的运行配置,请参见this answer

如果你真的想从Maven运行,那么在将jvmArg参数添加到pom.xml之后,你需要运行该插件:

mvm scala:run -Dlauncher=MyClassName

注意:在你放置MyClassName的地方,实际上是启动器的名称,而不是类名。对于许多项目,人们选择合理的名称作为启动器,这使它们经常与类的本地名称重合。但如果你想的话,你也可以称之为MyLauncher。
阅读maven-scala-plugin的文档可能会对你有所帮助。

在修改pom文件之后,我会从终端调用mvn clean和mvn install。但是我会使用IDEA的Run按钮。实际上,我想使用IDEA的Debug功能来观察一些变量,并发现软件输出错误的来源。这是无法通过终端实现的(据我所知)。 - Alexandre Cançado Cardoso
使用您之前提到的终端mvn命令也会产生错误。 - Alexandre Cançado Cardoso
1
你尝试过在终端中设置 export MAVEN_OPTS=-Xmx2G 吗? - Pablo Mendes

0

以上的答案都对我没用。有效的方法是从Intellij支持论坛中找到了this answer。它建议通过进入Build, Execution, Deployment > Compiler > Build Process heap size(Mbytes)来将构建过程堆大小增加到1024 MB。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接