Java "OutOfMemoryError: GC overhead limit exceeded" in CI
GC overhead limit exceeded is a heap-pressure signal: the JVM spent over 98% of recent time in garbage collection while recovering under 2% of the heap. It is effectively thrashing - almost out of memory but not yet fully exhausted.
What this error means
A build or test fails with java.lang.OutOfMemoryError: GC overhead limit exceeded. It often follows a long slowdown as GC churns, on memory-heavy compilation, annotation processing, or large test fixtures.
java.lang.OutOfMemoryError: GC overhead limit exceeded
at java.base/java.util.Arrays.copyOf(Arrays.java:3537)
at com.example.Loader.readAll(Loader.java:44)Common causes
Heap too small for the workload
The configured -Xmx is too low for the build/test's live data; the collector keeps running but cannot free enough, so it gives up.
Excessive allocation or a leak
Loading huge files into memory, unbounded caches, or accumulating fixtures inflates live data until GC cannot keep pace.
How to fix it
Raise heap for the build/test JVM
Increase -Xmx within the runner's limits for the right tool.
# Maven build/test JVM:
env:
MAVEN_OPTS: -Xmx2g
# Gradle test workers:
# test { maxHeapSize = '2g' }Reduce allocation pressure
- Stream large inputs instead of reading them fully into memory.
- Bound caches and clear large test fixtures between cases.
- If the heap is genuinely sufficient, capture a heap dump (
-XX:+HeapDumpOnOutOfMemoryError) to find a leak.
How to prevent it
- Set realistic
-Xmxfor build and test JVMs, stream large data, and bound caches so the collector is not perpetually thrashing.