Files
Claude e83c9949d8 Add jdk27-memory: compact object headers and G1-everywhere on a Spring Boot service
Spring Boot 4.1.1 catalog service measured on JDK 25, 26 and 27: live heap 320 MB to 273 MB with compact headers, per-class bytes per instance, container-sizing sweeps with real cgroup limits, 1-CPU Serial vs G1 with Native Memory Tracking, removed flags (MaxRAM, UseCompressedClassPointers), and a kernel OOM-kill check. Outputs in jdk27-memory/output.

Co-Authored-By: Claude Sonnet 5 <[email protected]>
Claude-Session: https://claude.ai/code/session_01TF9JWFvJSNm6HVzswzZU5a
2026-09-24 15:09:55 +00:00

45 lines
2.4 KiB
Bash
Executable File

#!/usr/bin/env bash
# JEP 523 in a small container: 1 CPU, 1 GB. JDK 26 picks Serial here, JDK 27 picks G1. What does the app
# cost under each collector, and what does the JVM say it spends outside the heap (Native Memory Tracking)?
# usage: one-cpu.sh [N products] [runs]
source "$(dirname "$0")/lib.sh"
N="${1:-2000000}"; RUNS="${2:-3}"
TMP="$(mktemp -d)"
MB=$((1024*1024))
export NMT=1 CG_MEM=$((1024*MB)) CG_CPUS=1
nmt() { # file -> "GC committed KB|Total committed KB"
local gc tot
gc=$(awk '/^- *GC \(reserved/ {gsub(/[^0-9=]/," "); n=split($0,a,"="); print a[3]+0; exit}' "$1")
tot=$(awk '/^Total: reserved/ {gsub(/[^0-9=]/," "); n=split($0,a,"="); print a[3]+0; exit}' "$1")
echo "$gc|$tot"
}
row() { # label jdk flags...
local label="$1" jh="$2"; shift 2
local st=() live=() rss=() gcn=() gcms=() ld=() gck=() totk=() coll="" cpus=""
for r in $(seq 1 "$RUNS"); do
d="$TMP/$label-$r"
run_app "$jh" "$N" "$d" -XX:MaxRAMPercentage=50 "$@" >/dev/null 2>&1 || { echo "$label run $r FAILED: $(cat "$d/outcome.txt")"; return; }
coll=$(kv "$d/memory.txt" collectors); cpus=$(kv "$d/memory.txt" availableProcessors)
st+=("$(grep -o '[0-9.]*' "$d/startup.txt" | tail -1)")
live+=("$(kv "$d/memory.txt" heapLiveAfterGcMB)"); rss+=("$(kv "$d/memory.txt" rssMB)")
gcn+=("$(kv "$d/load.txt" gcCountDuringLoad)"); gcms+=("$(kv "$d/load.txt" gcMillisDuringLoad)")
ld+=("$(kv "$d/load.txt" loadMillis)")
IFS='|' read -r g t <<<"$(nmt "$d/nmt.txt")"; gck+=("$g"); totk+=("$t")
done
m() { printf '%s\n' "$@" | median; }
printf '%s\n collectors=%s cpus=%s\n' "== $label" "$coll" "$cpus"
printf ' startup=%ss live=%sMB rss=%sMB loadMillis=%s gcDuringLoad=%s (%sms)\n' \
"$(m "${st[@]}")" "$(m "${live[@]}")" "$(m "${rss[@]}")" "$(m "${ld[@]}")" "$(m "${gcn[@]}")" "$(m "${gcms[@]}")"
printf ' NMT: GC committed=%s KB Total committed=%s KB\n\n' "$(m "${gck[@]}")" "$(m "${totk[@]}")"
}
echo "# $N products, container = 1 GB / 1 CPU (cgroup), -XX:MaxRAMPercentage=50 (512 MB heap), NMT summary on, medians of $RUNS runs"
row "jdk26-default (the JVM chose)" "$JDK26"
row "jdk26 -XX:+UseG1GC" "$JDK26" -XX:+UseG1GC
row "jdk27-default (the JVM chose)" "$JDK27"
row "jdk27 -XX:+UseSerialGC" "$JDK27" -XX:+UseSerialGC
row "jdk27 -XX:+UseSerialGC, compact off" "$JDK27" -XX:+UseSerialGC -XX:-UseCompactObjectHeaders
rm -rf "$TMP"