From ea459bc51e503e3a3a52a19d44c3d1b1287f4c95 Mon Sep 17 00:00:00 2001 From: Claude Date: Thu, 24 Sep 2026 17:22:12 +0000 Subject: [PATCH] ci: cut only the Kotlin daemon heap, not Gradle's MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Correcting cdb4f1f7, which capped both to 4g and traded one OOM for another. The diagnosis was right: test-and-build-android was dying of memory. gradle.properties asks for -Xmx6g (Gradle) plus -Xmx8g and 2g metaspace (Kotlin daemon), roughly 16GB of ceiling on a 16GB runner, and that job is the only one heavy enough to reach it. Capping both did stop the runner deaths — the job ran 61 minutes and reached R8 and lint, where it used to die at 11 to 14 minutes during compile. But it then failed with java.lang.OutOfMemoryError: Java heap space in minifyPlayBenchmarkWithR8 and lintAnalyzePlayBenchmark. Both draw on the Gradle daemon's heap, and 4g is not enough for them on this app. 6g always was — they never OOMed in the five earlier runs; the system did. So the cut belongs entirely on the Kotlin daemon: 8g + 2g metaspace down to 4g + 1g, Gradle left at its 6g default. Total ceiling ~11GB instead of ~16GB, which leaves the runner headroom without starving R8. Confirmation signals stay falsifiable: if the runner dies early again, the ceiling is still too high; if R8 or lint OOM again, 6g is not enough either and the job needs splitting rather than tuning. Co-Authored-By: Claude Opus 5 Claude-Session: https://claude.ai/code/session_01AXvKXakvup4inNFfAhhr4L --- .github/workflows/build.yml | 27 ++++++++++++++------------- 1 file changed, 14 insertions(+), 13 deletions(-) diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml index faf7452235..1a123e7e16 100644 --- a/.github/workflows/build.yml +++ b/.github/workflows/build.yml @@ -380,24 +380,25 @@ jobs: # variants are compile-equivalent for unit-test purposes; running all six # adds ~5× the kotlinc work without catching new defects on PRs. Push to # main still gets the full test matrix via the production-build path. - # Memory caps, CI-only. gradle.properties asks for -Xmx6g (Gradle) plus - # -Xmx8g and 2g metaspace (Kotlin daemon), which is ~16GB of ceiling on a - # 16GB ubuntu-latest runner before the launcher JVM, Lint's fork and the - # KSP workers are counted. Every other job stays well under it; this one - # runs two lint variants, two flavours of unit tests and - # assembleBenchmark, and it is the only job that has died — five times, - # each mid-compile or mid-lint, reported as "the runner has received a - # shutdown signal", which is what the Linux OOM killer taking the runner - # agent looks like from the outside. + # Memory, CI-only. gradle.properties asks for -Xmx6g (Gradle) plus -Xmx8g + # and 2g metaspace (Kotlin daemon) — about 16GB of ceiling on a 16GB + # ubuntu-latest runner, before the launcher JVM, Lint's fork and the KSP + # workers. This job is the only one heavy enough to reach it, and it died + # five times mid-compile with "the runner has received a shutdown signal", + # which is the OOM killer taking the runner agent. + # + # Only the Kotlin daemon is cut. An earlier attempt capped BOTH to 4g and + # traded one OOM for another: the runner survived and the job ran to + # completion, but R8 and lintAnalyze then failed with + # "java.lang.OutOfMemoryError: Java heap space" — they draw on the Gradle + # daemon's heap, and 4g is not enough for them on this app. 6g always was, + # so it stays; 8g + 2g for kotlinc is the part that did not fit. # # Overridden here rather than in gradle.properties so local builds on - # bigger machines keep the headroom. 4g apiece was verified to complete - # lintFdroidBenchmark and both unit-test tasks; it trades some build time - # for a job that finishes. + # bigger machines keep the headroom. - name: Test + Build Android (gradle) run: | ./gradlew \ - -Dorg.gradle.jvmargs="-Xmx4g -Dfile.encoding=UTF-8" \ -Dkotlin.daemon.jvmargs="-Xmx4g -XX:MaxMetaspaceSize=1g" \ :amethyst:lintFdroidBenchmark \ :amethyst:lintPlayBenchmark \